Migrating from SLF4J
SLF4J is a logging API whose reference implementation is Logback, just like Log4j API is a logging API whose reference implementation is Log4j Core. In this page we will guide you through migrating from SLF4J to Log4j API as your logging API.
Instead of migrating your logging API, SLF4J, are you looking for migrating your logging implementation, Logback? Please refer to Migrating from Logback. |
Struggling with the logging API, implementation, and bridge concepts? Click for an introduction.
- Logging API
-
A logging API is an interface your code or your dependencies directly logs against. It is required at compile-time. It is implementation agnostic to ensure that your application can write logs, but is not tied to a specific logging implementation. Log4j API, SLF4J, JUL (Java Logging), JCL (Apache Commons Logging), JPL (Java Platform Logging) and JBoss Logging are major logging APIs.
- Logging implementation
-
A logging implementation is only required at runtime and can be changed without the need to recompile your software. Log4j Core, JUL (Java Logging), Logback are the most well-known logging implementations.
- Logging bridge
-
Logging implementations accept input from a single logging API of their preference; Log4j Core from Log4j API, Logback from SLF4J, etc. A logging bridge is a simple logging implementation of a logging API that forwards all messages to a foreign logging API. Logging bridges allow a logging implementation to accept input from other logging APIs that are not their primary logging API. For instance,
log4j-slf4j2-impl
bridges SLF4J calls to Log4 API and effectively enables Log4j Core to accept input from SLF4J.
To make things a little bit more tangible, consider the following visualization of a typical Log4j Core installation with bridges for an application:
@startuml frame "Compile time" { [Application] --> [Log4j API] : logs to [Log4j API] #Cyan [SLF4J] #Cyan [Library 1] --> [SLF4J] : logs to [Application] --> [Library 1] : uses [Application] --> [Library 2] : uses [Application] --> [Library 3] : uses } frame Runtime { [Log4j Core] <.. [Log4j API] : is implemented by [Log4j Core] <.. (log4j2.xml) : is provided to [Log4j Core] #LightGreen [JPL-to-Log4j] ..> [Log4j Core] : forwards to [JPL-to-Log4j] #Yellow [SLF4J-to-Log4j] ..> [Log4j Core] : forwards to [SLF4J-to-Log4j] #Yellow [JUL-to-Log4j] ..> [Log4j Core] : forwards to [JUL-to-Log4j] #Yellow frame JRE { [JPL] #Cyan [JUL] #Cyan } } [Library 2] --> [JUL] : logs to [Library 3] --> [JPL] : logs to [JPL] ..> [JPL-to-Log4j] : is implemented by [JUL] ..> [JUL-to-Log4j] : is implemented by [SLF4J] ..> [SLF4J-to-Log4j] : is implemented by legend top right | <#LightGreen> | Logging implementation | | <#Yellow> | Logging bridge | | <#Cyan> | Logging API | | <size:18><U+2192></size> | Compile-time usage | | <size:18><U+21E2></size> | Runtime usage | endlegend @enduml
Migrating
If your application or library logs using SLF4J, you can migrate it to Log4j API as follows:
-
Remove
org.slf4j:slf4j-api
dependency -
Follow the instructions shared in the "Getting started" page for installing
log4j-api
and using it -
Search for
org.slf4j
usages in your project and replace them with Log4j API equivalentsFor an exhaustive list of code changes that need to be carried out, refer to the SLF4J to Log4j API migration OpenRewrite recipe. This you can use to
-
either manually follow the described migrations,
-
or run OpenRewrite to automatically migrate the code.
org.slf4j.LoggerFactory
-
Replace its usages with
org.apache.logging.log4j.LogManager
. Note thatLogManager.getLogger(Foo.class)
can be simplified asLogManager.getLogger()
, ifFoo
is the enclosing class of the field. org.slf4j.Logger
-
Replace its usages with
org.apache.logging.log4j.Logger
. Since SLF4J’sLogger
is almost a parent of Log4j’sLogger
, most methods should work without any changes. org.slf4j.MDC
-
Replace its usages with
org.apache.logging.log4j.ThreadContext
.
-
-
If you use
@Slf4j
from Lombok, you need to replace them with@Log4j2
instead.
At this stage, you should have your application or library logging using Log4j API.
- If it is a library that you migrated,
-
then you don’t need to take any extra steps. Unlike applications, libraries should be logging implementation agnostic. That is, libraries should log through a logging API, but leave the decision of the logging implementation to the application.
- If it is an application that you migrated, and you are not using Log4j Core as your logging implementation,
-
then you can consider doing so. Certain Log4j API features (e.g., garbage-free logging) require an end-to-end setup which is mostly possible using Log4j API in combination with Log4j Core.
See Installation for installing Log4j Core.
If you are using Logback, refer to Migrating from Logback.