Log4j2 Sample Config

Previous release had a Sift appender which could be used for multiple bundles and each writing to separate log file based on bundle name. How do we achieve this using OpenHAB 2.2 with log4j2?

See first post “Custom config”

Thanks. I saw that post, but there separate loggers (e.g. KNX, ZWave etc) are created for each bundle.

I would prefer to create a single logger and use it for multiple bundle. For OpenHAB 2.1, I was using following in my org.ops4j.pax.logging.cfg file:

// Shared sift appender
log4j.appender.sift=org.apache.log4j.sift.MDCSiftingAppender
log4j.appender.sift.key=bundle.name
log4j.appender.sift.default=openhab
log4j.appender.sift.appender=org.apache.log4j.FileAppender
log4j.appender.sift.appender.layout=org.apache.log4j.PatternLayout
log4j.appender.sift.appender.layout.ConversionPattern=%d{yyyy-MM-dd HH:mm:ss.SSS} [%-5.5p] [%t] [%-36.36c] - %m%n
log4j.appender.sift.appender.file=${openhab.logdir}/${bundle.name}.log
log4j.appender.sift.appender.append=true

// Refer above sift appender in each of my custom bundle
log4j.logger.mycustombundle1=INFO, sift
log4j.logger.mycustombundle2=INFO, sift
log4j.logger.mycustombundle3=INFO, sift
log4j.logger.mycustombundle4=INFO, sift

Thank you @Dim

1 Like

Hi All,
there are many logging related threads but this seems most relevant to my case. I want to have 2 different custom loggers but appending to the same file. I know how to make them appending to different files but since they are related to the same binding I want them to land in single file.
This is related to eBUS binding which logs to different patterns (the below was produced by myself and logs to separate files as you can see):

### Custom Loggers ###
# EBUS
log4j2.logger.eBus.name = org.openhab.binding.ebus
log4j2.logger.eBus.level = WARN
log4j2.logger.eBus.additivity = false
log4j2.logger.eBus.appenderRefs = eBus
log4j2.logger.eBus.appenderRef.eBus.ref = EBUS

# CSDEV
log4j2.logger.csdev.name = de.csdev.ebus
log4j2.logger.csdev.level = DEBUG
log4j2.logger.csdev.additivity = false
log4j2.logger.csdev.appenderRefs = csdev
log4j2.logger.csdev.appenderRef.eBus.ref = CSDEV

### Custom Appenders ###
# EBUS
log4j2.appender.eBus.name = EBUS
log4j2.appender.eBus.type = RollingRandomAccessFile
log4j2.appender.eBus.fileName = ${openhab.logdir}/ebus.log
log4j2.appender.eBus.filePattern = ${openhab.logdir}/ebus.log.%i
log4j2.appender.eBus.immediateFlush = true
log4j2.appender.eBus.append = true
log4j2.appender.eBus.layout.type = PatternLayout
log4j2.appender.eBus.layout.pattern = %d{dd-MMM-yyyy HH:mm:ss.SSS} [%-5.5p] [%-50.50c] - %m%n
log4j2.appender.eBus.policies.type = Policies
log4j2.appender.eBus.policies.size.type = SizeBasedTriggeringPolicy
log4j2.appender.eBus.policies.size.size = 10MB
log4j2.appender.eBus.strategy.type = DefaultRolloverStrategy
log4j2.appender.eBus.strategy.max = 10

# CSDEV
log4j2.appender.csdev.name = CSDEV
log4j2.appender.csdev.type = RollingRandomAccessFile
log4j2.appender.csdev.fileName = ${openhab.logdir}/csdev.log
log4j2.appender.csdev.filePattern = ${openhab.logdir}/csdev.log.%i
log4j2.appender.csdev.immediateFlush = true
log4j2.appender.csdev.append = true
log4j2.appender.csdev.layout.type = PatternLayout
log4j2.appender.csdev.layout.pattern = %d{dd-MMM-yyyy HH:mm:ss.SSS} [%-5.5p] [%-50.50c] - %m%n
log4j2.appender.csdev.policies.type = Policies
log4j2.appender.csdev.policies.size.type = SizeBasedTriggeringPolicy
log4j2.appender.csdev.policies.size.size = 10MB
log4j2.appender.csdev.strategy.type = DefaultRolloverStrategy
log4j2.appender.csdev.strategy.max = 10


how to make it to get appended to the same file? I can’t find good manual describing the logging config, and by looking how it looks in other places but I have to say I am closer to intuition than true firm understanding of how to control it.

Hi @witek_1308,

I have described this in one of my blog posts. Unfortunately it´s in german but i think you can adopt the code samples easily.

Best regards!

http://cleveres-heim.de/howto/openhab-2-3-log4j2-beispiel-konfiguration-knx-binding-logger/

I cant get this to work…
I´m trying to custom log zigbee and zsmart systems into a seperate logfile. The logfile gets created all right, but it´s a 0 byte file, not updating…

This is what I´ve added to the default org.ops4j.pax.logging.cfg

# Zigbee
log4j2.logger.ZSmart.name = com.zsmartsystems.zigbee
log4j2.logger.ZSmart.level = DEBUG
log4j2.logger.ZSmart.additivity = false
log4j2.logger.ZSmart.appenderRefs = ZSmart
log4j2.logger.ZSmart.appenderRef.ZSmart.ref = ZIGBEE

log4j2.logger.Zigbee.name = org.openhab.binding.zigbee
log4j2.logger.Zigbee.level = DEBUG
log4j2.logger.Zigbee.additivity = false
log4j2.logger.Zigbee.appenderRefs = Zigbee
log4j2.logger.Zigbee.appenderRef.Zigbee.ref = ZIGBEE

# Zigbee
log4j2.appender.ZWave.name = ZIGBEE
log4j2.appender.ZWave.type = RollingRandomAccessFile
log4j2.appender.ZWave.fileName = /var/log/openhab2/Zigbee.log
log4j2.appender.ZWave.filePattern = /var/log/openhab2/Zigbee.log.%i
log4j2.appender.ZWave.immediateFlush = true
log4j2.appender.ZWave.append = true
log4j2.appender.ZWave.layout.type = PatternLayout
log4j2.appender.ZWave.layout.pattern = %d{dd-MMM-yyyy HH:mm:ss.SSS} [%-5.5p] [%-50.50c] - %m%n
log4j2.appender.ZWave.policies.type = Policies
log4j2.appender.ZWave.policies.size.type = SizeBasedTriggeringPolicy
log4j2.appender.ZWave.policies.size.size = 10MB
log4j2.appender.ZWave.strategy.type = DefaultRolloverStrategy
log4j2.appender.ZWave.strategy.max = 10

Anyone know why it isnt updating the Zigbee.log file??
I did turn on DEBUG level in karaf consol.

Check your appender… you have zwave in there :wink:

FYI, modifying the logging through Karaf will update this file. You can change logging level through Karaf or by manually modifying the file.

Arrgh damit… I tired another appender, forgot to remove the Zwave…
Anyway, it´s removed now. But the Zigbee file still doesnt update.

# Zigbee
log4j2.logger.ZSmart.name = com.zsmartsystems.zigbee
log4j2.logger.ZSmart.level = DEBUG
log4j2.logger.ZSmart.additivity = false
log4j2.logger.ZSmart.appenderRefs = ZSmart
log4j2.logger.ZSmart.appenderRef.ZSmart.ref = ZIGBEE

log4j2.logger.Zigbee.name = org.openhab.binding.zigbee
log4j2.logger.Zigbee.level = DEBUG
log4j2.logger.Zigbee.additivity = false
log4j2.logger.Zigbee.appenderRefs = Zigbee
log4j2.logger.Zigbee.appenderRef.Zigbee.ref = ZIGBEE

# Zigbee
log4j2.appender.Zigbee.name = ZIGBEE
log4j2.appender.Zigbee.type = RollingRandomAccessFile
log4j2.appender.Zigbee.fileName = /var/log/openhab2/Zigbee.log
log4j2.appender.Zigbee.filePattern = /var/log/openhab2/Zigbee.log.%i
log4j2.appender.Zigbee.immediateFlush = true
log4j2.appender.Zigbee.append = true
log4j2.appender.Zigbee.layout.type = PatternLayout
log4j2.appender.Zigbee.layout.pattern = %d{dd-MMM-yyyy HH:mm:ss.SSS} [%-5.5p] [%-50.50c] - %m%n
log4j2.appender.Zigbee.policies.type = Policies
log4j2.appender.Zigbee.policies.size.type = SizeBasedTriggeringPolicy
log4j2.appender.Zigbee.policies.size.size = 10MB
log4j2.appender.Zigbee.strategy.type = DefaultRolloverStrategy
log4j2.appender.Zigbee.strategy.max = 10

After your last change, try an OH restart. Some changes to the logging config require it. If that does not work, double check permissions in the directories you are writing to.

I have changed the config file to use the same path as the event logs etc… This should eliminate any problems with permissions, I would say.
The config looks like this now:

# Zigbee
log4j2.logger.ZSmart.name = com.zsmartsystems.zigbee
log4j2.logger.ZSmart.level = DEBUG
log4j2.logger.ZSmart.additivity = false
log4j2.logger.ZSmart.appenderRefs = ZSmart
log4j2.logger.ZSmart.appenderRef.ZSmart.ref = ZIGBEE

log4j2.logger.Zigbee.name = org.openhab.binding.zigbee
log4j2.logger.Zigbee.level = DEBUG
log4j2.logger.Zigbee.additivity = false
log4j2.logger.Zigbee.appenderRefs = Zigbee
log4j2.logger.Zigbee.appenderRef.Zigbee.ref = ZIGBEE

# Zigbee
log4j2.appender.Zigbee.name = ZIGBEE
log4j2.appender.Zigbee.type = RollingRandomAccessFile
log4j2.appender.Zigbee.fileName = ${openhab.logdir}/Zigbee.log
log4j2.appender.Zigbee.filePattern = ${openhab.logdir}/Zigbee.log.%i
log4j2.appender.Zigbee.immediateFlush = true
log4j2.appender.Zigbee.append = true
log4j2.appender.Zigbee.layout.type = PatternLayout
log4j2.appender.Zigbee.layout.pattern = %d{dd-MMM-yyyy HH:mm:ss.SSS} [%-5.5p] [%-50.50c] - %m%n
log4j2.appender.Zigbee.policies.type = Policies
log4j2.appender.Zigbee.policies.size.type = SizeBasedTriggeringPolicy
log4j2.appender.Zigbee.policies.size.size = 10MB
log4j2.appender.Zigbee.strategy.type = DefaultRolloverStrategy
log4j2.appender.Zigbee.strategy.max = 10

Zigbee.log still doesn´t update though… Will try a reboot in 2 minutes.

Nope, it still doesnt update Zigbee.log file after an reboot… Hrmpf!! :frowning:

Everything looks fine to me. The only thing I’m not sure of are the use of variables… but if it works for other people…

If you change the logging level for the binding in Karaf, do you see the change reflected in the file? Make sure you don’t have any other loggers for the binding.

I changed to variable, cause the other appenders are using the variable… I would have thought that this is the correct way of doing it, avoiding any conflic with permission etc…

This is the full (default) of my logging config file, and Zigbee added at the bottom:

# Common pattern layout for appenders
#log4j2.pattern = %d{ISO8601} | %-5p | %-16t | %-32c{1} | %X{bundle.id} - %X{bundle.name} - %X{bundle.version} | %m%n

# Root logger
log4j2.rootLogger.level = WARN
log4j2.rootLogger.appenderRefs = out, osgi
log4j2.rootLogger.appenderRef.out.ref = LOGFILE
log4j2.rootLogger.appenderRef.osgi.ref = OSGI

# Karaf Shell logger
log4j2.logger.shell.name = org.apache.karaf.shell.support
log4j2.logger.shell.level = OFF
log4j2.logger.shell.appenderRefs = stdout
log4j2.logger.shell.appenderRef.stdout.ref = STDOUT

# Security audit logger
log4j2.logger.audit.name = org.apache.karaf.jaas.modules.audit
log4j2.logger.audit.level = INFO
log4j2.logger.audit.additivity = false
log4j2.logger.audit.appenderRefs = audit
log4j2.logger.audit.appenderRef.audit.ref = AUDIT

# openHAB specific logger configuration

log4j2.logger.openhab.name = org.openhab
log4j2.logger.openhab.level = INFO

log4j2.logger.smarthome.name = org.eclipse.smarthome
log4j2.logger.smarthome.level = INFO

log4j2.logger.smarthomeItemStateEvent.name = smarthome.event.ItemStateEvent
log4j2.logger.smarthomeItemStateEvent.level = ERROR
log4j2.logger.smarthomeItemAddedEvent.name = smarthome.event.ItemAddedEvent
log4j2.logger.smarthomeItemAddedEvent.level = ERROR
log4j2.logger.smarthomeItemRemovedEvent.name = smarthome.event.ItemRemovedEvent
log4j2.logger.smarthomeItemRemovedEvent.level = ERROR
log4j2.logger.smarthomeThingStatusInfoEvent.name = smarthome.event.ThingStatusInfoEvent
log4j2.logger.smarthomeThingStatusInfoEvent.level = ERROR
log4j2.logger.smarthomeThingAddedEvent.name = smarthome.event.ThingAddedEvent
log4j2.logger.smarthomeThingAddedEvent.level = ERROR
log4j2.logger.smarthomeThingRemovedEvent.name = smarthome.event.ThingRemovedEvent
log4j2.logger.smarthomeThingRemovedEvent.level = ERROR
log4j2.logger.smarthomeInboxUpdatedEvent.name = smarthome.event.InboxUpdatedEvent
log4j2.logger.smarthomeInboxUpdatedEvent.level = ERROR

log4j2.logger.events.name = smarthome.event
log4j2.logger.events.level = INFO
log4j2.logger.events.additivity = false
log4j2.logger.events.appenderRefs = event
log4j2.logger.events.appenderRef.event.ref = EVENT
log4j2.logger.events.appenderRef.osgi.ref = OSGI

log4j2.logger.jupnp.name = org.jupnp
log4j2.logger.jupnp.level = ERROR

log4j2.logger.jmdns.name = javax.jmdns
log4j2.logger.jmdns.level = ERROR

# This suppresses all Maven download issues from the log when doing feature installations
# as we are logging errors ourselves in a nicer way anyhow.
log4j2.logger.paxurl.name = org.ops4j.pax.url.mvn.internal.AetherBasedResolver
log4j2.logger.paxurl.level = ERROR

# Filters known issues of pax-web (issue link to be added here).
# Can be removed once the issues are resolved in an upcoming version.
log4j2.logger.paxweb.name = org.ops4j.pax.web.pax-web-runtime
log4j2.logger.paxweb.level = OFF

# Filters known issues of lsp4j, see
# https://github.com/eclipse/smarthome/issues/4639
# https://github.com/eclipse/smarthome/issues/4629
# https://github.com/eclipse/smarthome/issues/4643
# Can be removed once the issues are resolved in an upcoming version.
log4j2.logger.lsp4j.name = org.eclipse.lsp4j
log4j2.logger.lsp4j.level = OFF

# Filters known issues of KarServiceImpl, see
# https://github.com/openhab/openhab-distro/issues/519#issuecomment-351944506
# Can be removed once the issues are resolved in an upcoming version.
log4j2.logger.karservice.name = org.apache.karaf.kar.internal.KarServiceImpl
log4j2.logger.karservice.level = ERROR


# Appenders configuration

# Console appender not used by default (see log4j2.rootLogger.appenderRefs)
log4j2.appender.console.type = Console
log4j2.appender.console.name = STDOUT
log4j2.appender.console.layout.type = PatternLayout
log4j2.appender.console.layout.pattern = %d{HH:mm:ss.SSS} [%-5.5p] [%-36.36c] - %m%n

# Rolling file appender
log4j2.appender.out.type = RollingRandomAccessFile
log4j2.appender.out.name = LOGFILE
log4j2.appender.out.fileName = ${openhab.logdir}/openhab.log
log4j2.appender.out.filePattern = ${openhab.logdir}/openhab.log.%i
log4j2.appender.out.immediateFlush = true
log4j2.appender.out.append = true
log4j2.appender.out.layout.type = PatternLayout
log4j2.appender.out.layout.pattern = %d{yyyy-MM-dd HH:mm:ss.SSS} [%-5.5p] [%-36.36c] - %m%n
log4j2.appender.out.policies.type = Policies
log4j2.appender.out.policies.size.type = SizeBasedTriggeringPolicy
log4j2.appender.out.policies.size.size = 16MB

# Event log appender
log4j2.appender.event.type = RollingRandomAccessFile
log4j2.appender.event.name = EVENT
log4j2.appender.event.fileName = ${openhab.logdir}/events.log
log4j2.appender.event.filePattern = ${openhab.logdir}/events.log.%i
log4j2.appender.event.immediateFlush = true
log4j2.appender.event.append = true
log4j2.appender.event.layout.type = PatternLayout
log4j2.appender.event.layout.pattern = %d{yyyy-MM-dd HH:mm:ss.SSS} [%-26.26c] - %m%n
log4j2.appender.event.policies.type = Policies
log4j2.appender.event.policies.size.type = SizeBasedTriggeringPolicy
log4j2.appender.event.policies.size.size = 16MB

# Audit file appender
log4j2.appender.audit.type = RollingRandomAccessFile
log4j2.appender.audit.name = AUDIT
log4j2.appender.audit.fileName = ${openhab.logdir}/audit.log
log4j2.appender.audit.filePattern = ${openhab.logdir}/audit.log.%i
log4j2.appender.audit.append = true
log4j2.appender.audit.layout.type = PatternLayout
log4j2.appender.audit.layout.pattern = %d{yyyy-MM-dd HH:mm:ss.SSS} [%-5.5p] [%-36.36c] - %m%n
log4j2.appender.audit.policies.type = Policies
log4j2.appender.audit.policies.size.type = SizeBasedTriggeringPolicy
log4j2.appender.audit.policies.size.size = 8MB

# OSGi appender
log4j2.appender.osgi.type = PaxOsgi
log4j2.appender.osgi.name = OSGI
log4j2.appender.osgi.filter = *
log4j2.logger.org_openhab_binding_velux.level = INFO
log4j2.logger.org_openhab_binding_velux.name = org.openhab.binding.velux
log4j2.logger.org_openhab_binding_zigbee.name = org.openhab.binding.zigbee
log4j2.logger.com_zsmartsystems_zigbee.name = com.zsmartsystems.zigbee
log4j2.logger.org_openhab_binding_zigbee.level = DEBUG
log4j2.logger.com_zsmartsystems_zigbee.level = DEBUG
log4j2.logger.org_openhab_binding_zwave.level = OFF
log4j2.logger.org_openhab_binding_zwave.name = org.openhab.binding.zwave

# Zigbee
log4j2.logger.ZSmart.name = com.zsmartsystems.zigbee
log4j2.logger.ZSmart.level = DEBUG
log4j2.logger.ZSmart.additivity = false
log4j2.logger.ZSmart.appenderRefs = ZSmart
log4j2.logger.ZSmart.appenderRef.ZSmart.ref = ZIGBEE

log4j2.logger.Zigbee.name = org.openhab.binding.zigbee
log4j2.logger.Zigbee.level = DEBUG
log4j2.logger.Zigbee.additivity = false
log4j2.logger.Zigbee.appenderRefs = Zigbee
log4j2.logger.Zigbee.appenderRef.Zigbee.ref = ZIGBEE

# Zigbee
log4j2.appender.Zigbee.name = ZIGBEE
log4j2.appender.Zigbee.type = RollingRandomAccessFile
log4j2.appender.Zigbee.fileName = ${openhab.logdir}/zigbee.log
log4j2.appender.Zigbee.filePattern = ${openhab.logdir}/zigbee.log.%i
log4j2.appender.Zigbee.immediateFlush = true
log4j2.appender.Zigbee.append = true
log4j2.appender.Zigbee.layout.type = PatternLayout
log4j2.appender.Zigbee.layout.pattern = %d{dd-MMM-yyyy HH:mm:ss.SSS} [%-5.5p] [%-50.50c] - %m%n
log4j2.appender.Zigbee.policies.type = Policies
log4j2.appender.Zigbee.policies.size.type = SizeBasedTriggeringPolicy
log4j2.appender.Zigbee.policies.size.size = 10MB
log4j2.appender.Zigbee.strategy.type = DefaultRolloverStrategy
log4j2.appender.Zigbee.strategy.max = 10

But it doesnt seem to work.

Just above the first # Zigbee, there is a #OSGi appender… What does it do? It has the zigbee and zsmartsystem as well… Could this be a conflic?

I started debug logging from Karaf consol before I made the reboot. But the file is is still empty…
Another thing…
I deleted the file, just to see if openhab will create a new one…
At first it didn´t… Then I tried searching for the file zigbee.log… The searching found two zigbee.log file in these paths:

But they´re still both 0 bytes files :frowning:

Yes… absolutely. That’s was why I asked if you had any other loggers for the binding. Removing those should help!

1 Like

You did, But I had no idea what it did… It didnt have a path entry, so I thought it was something else…

Anyway… It seems to be working now… zigbee.log file is no longer a 0 byte, and it´s updating.
Also my tail log screen is no longer filled with debug logging from zigbee and zsmarsystems :slight_smile:

So, Once again you helped me through, Scott! :smile:

1 Like

This is old, but may help someone - I found that I could suppress a specific event.log message by adding filtering to the event appender - YMMV, but seems to work for me

Edit your org.ops4j.pax.logging.cfg file - mine is in /var/lib/openhab2/etc

# Event log appender
log4j2.appender.event.type = RollingRandomAccessFile
log4j2.appender.event.name = EVENT
log4j2.appender.event.fileName = ${openhab.logdir}/events.log
log4j2.appender.event.filePattern = ${openhab.logdir}/events.log.%i

log4j2.appender.event.filter.regex.type = RegexFilter
log4j2.appender.event.filter.regex.regex = .*Temperature changed.*
log4j2.appender.event.filter.regex.onMatch = DENY
log4j2.appender.event.filter.regex.onMisMatch = ACCEPT

log4j2.appender.event.immediateFlush = true
log4j2.appender.event.append = true
log4j2.appender.event.layout.type = PatternLayout
log4j2.appender.event.layout.pattern = %d{yyyy-MM-dd HH:mm:ss.SSS} [%-26.26c] - %m%n
log4j2.appender.event.policies.type = Policies
log4j2.appender.event.policies.size.type = SizeBasedTriggeringPolicy
log4j2.appender.event.policies.size.size = 16MB

Note that docs here show …regex.onMismatch - but I could only get it to work with …regex.onMisMatch (with 2 captial M’s)

Is it possible to force OH to begin writing to a new log file without stopping and starting OH?

I have set up a few custom loggers. They merily log, rotate log files, and archive. But every so often, when I am collaborating with a particular binding maintainer, I want to provide a “fresh” log file without incurring the OH restart and any potential “resetting” of the state of the binding that might accompany doing so. I want to cause the current log file to be renamed to logfile.log.n+1 and for new logging to start being written to logfile.log.

I am familiar with Karaf Console commands to manage logging (clear, tail, set, etc.). I didn’t see anything explicitly to trigger a file close and a new file creation/open.

Mike

Personally what I do is configure the binding to log to it’s own log file. If you just delete the .log file it will create a new one. Note, I don’t think you can just move it or rename it because OH will not see that and continue writing to the old file.

I’m not positive this will work but it is what I would try.

Don’t take my response as a definitive answer, but I am not aware of a way to do this. I’ve also found that deleting the current log file seems to occasionally hang the logging. I usually just manually trim up the log file to send to the dev.

You could try temporarily moving the appender to a different file, but IIRC, this also requires a restart. But there may be a way to just restart jog4j…