简体   繁体   中英

How to force log4j to be used but not slf4j

EDIT: To clarify the question, I added many explanations.

In my project dependencies, I have both slf4j and log4j . This can't be changed for some technical reason.

>gradlew dependencies
Starting a Gradle Daemon, 1 incompatible and 1 stopped Daemons could 
not be reused, use --status for details
> Task :dependencies
.
.
|    |         |    +--- org.springframework.boot:spring-boot-starter-logging:2.5.7
|    |         |    |    +--- ch.qos.logback:logback-classic:1.2.7
|    |         |    |    |    +--- ch.qos.logback:logback-core:1.2.7
|    |         |    |    |    \--- org.slf4j:slf4j-api:1.7.32
|    |         |    |    +--- org.apache.logging.log4j:log4j-to-slf4j:2.14.1
|    |         |    |    |    +--- org.slf4j:slf4j-api:1.7.25 -> 1.7.32
|    |         |    |    |    \--- org.apache.logging.log4j:log4j-api:2.14.1 -> 2.17.0
|    |         |    |    \--- org.slf4j:jul-to-slf4j:1.7.32
|    |         |    |         \--- org.slf4j:slf4j-api:1.7.32
.
.
+--- org.apache.logging.log4j:log4j-core:2.17.0
|    \--- org.apache.logging.log4j:log4j-api:2.17.0
+--- org.apache.logging.log4j:log4j-api:2.17.0
BUILD SUCCESSFUL in 16s
1 actionable task: 1 executed

I want to set the log level in the code , and AFAIK that can only be done with log4j . As a result, I simply look for a way to make this code line ( LogManager is part of log4j ) returns log4j implementation and not slf4j implementation:

import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
.
.
private final Logger logger = LogManager.getLogger(getClass());

Sadly, the logger's class returns is org.apache.logging.slf4j.SLF4JLogger :

System.out.println("logger class is: [" + logger.getClass() + "]");

output:

logger class is: [class org.apache.logging.slf4j.SLF4JLogger]

Even though it sounds easy, I haven't been able to do it or find an example online. What can be done?

Whats the full class path of LogManager? It has to be imported, there you should see the full class.

My guess is that you need to change the Import to import some log4j LogManager, not the slf4j one.

Log4j 2.x Core and the Log4j to SLF4J Adapter are two implementations of the Log4j 2.x API. If they are both present on the classpath log4j-to-slf4j is used. That is what happens in your case: messages logged using the Log4j 2.x API are sent to SLF4J, which sends them to Logback.

That is the standard logging configuration brought by the spring-boot-starter-logging . If you want to use Log4j 2 as backend instead you need to exclude that artifact and add spring-boot-starter-log4j2 .

Anyway, since you are using Spring Boot, you have two ways to set the level of a logger:

  1. Using Spring Boot's LoggingSystem abstraction (works for all available logging systems):

     final LoggingSystem loggingSystem = LoggingSystem.get(getClass().getClassLoader()); loggingSystem.setLogLevel("loggerName", LogLevel.DEBUG);
  2. Using the underlying logging system. In your case it is Logback, so you should use:

     final Logger logger = LoggerFactory.getLogger("loggerName"); if (logger instanceof ch.qos.logback.classic.Logger) { ((ch.qos.logback.classic.Logger) logger).setLevel(Level.DEBUG); }

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM