I have a systemd service file which run a docker container with log driver journald.
ExecStart=/usr/bin/docker run \
--name ${CONTAINER_NAME} \
-p ${PORT}:8080 \
--add-host ${DNS} \
-v /etc/localtime:/etc/localtime:ro \
--log-driver=journald \
--log-opt tag="docker.{{.Name}}" \
${RESPOSITORY_NAME}/${CONTAINER_NAME}
ExecStop=-/usr/bin/docker stop ${CONTAINER_NAME}
When I check the logs via journalctl I see two different _TRANSPORT. With journalctl -u test.service I see _TRANSPORT=stdout. And with Journalctl CONTAINER_NAME=test I see _TRANSPORT=journal
What is the difference?
The difference here is in how the logs get to
systemd-journald
before they are logged.As of right now, the supported transports (at least according to the
_TRANSPORT
field insystemd-journald
) are: audit, driver, syslog, journal, stdout and kernel (see systemd.journal-fields(7)).In your case, everything logged to
stdout
by commands executed by theExecStart=
andExecStop=
directives is logged under the_TRANSPORT=stdout
transport.However, Docker is internally capable of using the journald logging driver which, among other things, introduces several custom journal fields - one of them being
CONTAINER_ID=
. It's just a different method of delivering data tosystemd-journald
- instead of relying on systemd to catch and send everything from stdout tosystemd-journald
, Docker internally sends everything straight tosystemd-journald
by itself.This can be achieved by using the
sd-journal
API (as described in sd-journal(3)). Docker uses the go-systemd Go bindings for thesd-journal
C library.Simple example:
hello.c
Now if I check journal, I'll see both messages:
But each of them arrived using a different transport: