Search code examples
loggingdockersystemdrsyslog

Write journald metadata to rsyslog


I have a setup where docker containers use the journald log driver to write their logs. Currently log lines from the journal are forwarded to rsyslog running on the host, but the application name on the syslog lines appears as dockerd.

As a workaround, I'd like to write the CONTAINER_NAME field form the journal metadata into the line that appears in syslog, so I can identify what container wrote what line after the host's syslog has been shipped to a syslog aggregation server.

Any suggestions?


Solution

  • I was able to achieve this by defining a template after parsing the structured logs from journald. For figuring out what properties were available I ran journalctl -o verbose -n 10

    rsyslog has multiple different ways to do the same configuration, here is my config from a CentOS 7 machine:

    module(load="imjournal" StateFile="imjournal.state") # Load imjournal module
    module(load="mmjsonparse") # Load mmjsonparse module for structured logs
    
    action(type="mmjsonparse") # Attempt to parse JSON
    
    template(name="ContainerTemplate" type="list") {
        property(name="timestamp" dateFormat="rfc3339")
        constant(value=" ")
        property(name="$!CONTAINER_NAME")
        constant(value=" ")
        property(name="$!CONTAINER_ID")
        constant(value=" ")
        property(name="$!MESSAGE")
        constant(value="\n") # Separate logs with a newline
    }
    
    if ($!CONTAINER_NAME != "") then {
        action(type="omfile" file="/var/log/messages" template="ContainerFormat")
    } else {
        *.info;mail.none;news.none;authpriv.none;cron.none action(type="omfile" file="/var/log/messages")
    }
    

    Reference documentation: