1 Series Catalog

  • Introduction to JDK-Logging, log4J, and Logback logging
  • Commons-logging integrates with JDK-logging, log4j1, log4j2, and logback
  • The integration principle of SLF4J with JDK-Logging, log4j1, log4j2, logBack
  • Slf4j, JCL, juL, log4j1, log4j2, logback

2 Jar package summary

  • log4j1:

    • Log4j: The full contents of log4j1
  • log4j2:

    • Log4j-api: the API defined by log4j2
    • Log4j-core :log4j2 Implementation of the above API
  • logback:

    • Logback-core: indicates the core package of logback
    • Logback-classic: Logback implements the SLF4J API
  • commons-logging:

    • Commons-logging: The entire content of commons-logging
    • Log4j-jcl :commons-logging bridge to log4j2
    • Jcl-over-slf4j: Commons-logging bridge to SLf4J
  • Slf4j turns to some actual logging framework:

    Scenario description: If you are programming using the SLF4J API, the underlying intention is to use log4j1 for the actual logging output, which is what SLF4J-log4j12 does.

    • Slf4j-jdk14: Slf4J bridge to JDK-logging
    • Slf4j-log4j12: bridge slf4J to log4j1
    • Log4j-slf4j-impl: bridge slf4j to log4j2
    • Logback-classic: SLF4J bridge to logback
    • Slf4j-jcl: Slf4J bridge to Commons-logging
  • An actual logging framework switches to SLF4J:

    Scenario Description: If you use the LOG4j1 API to program, but want to output logs through logback, you need to pass the log output of log4j1 to SLf4J for output, and SLF4J to Logback for output. Pass the output of log4j1 to SLf4J, which is what log4J-over-SLf4j does

    This section focuses on switching between actual logging frameworks (more on that later)

    • Jul-to-slf4j: JDK-logging bridge to SLf4J
    • Log4j-over-slf4j: bridge from log4j1 to slf4j
    • Jcl-over-slf4j: Commons-logging bridge to SLf4J

3 Integration Summary

3.1 Commons-Logging integration with other logging frameworks

  • Commons-logging integration with JDK-logging:

    Jar packages required:

    • commons-logging
  • 2 Commons-logging integration with Log4j1:

    Jar packages required:

    • commons-logging
    • log4j
  • Commons-logging integration with Log4j2:

    Jar packages required:

    • commons-logging
    • log4j-api
    • log4j-core
    • Log4j-jcl (Integration package)
  • 4 Commons-Logging and Logback integration:

    Jar packages required:

    • logback-core
    • logback-classic
    • Slf4j-api, JCL-over-SLf4J (2 integration packages, can no longer require Commons-logging)
  • 5 Commons-Logging integration with SLF4J:

    Jar packages required:

    • Jcl-over-slf4j (integration package, no longer requires Commons-logging)
    • slf4j-api

3.2 SLF4J integration with other logging frameworks

  • Slf4j integration with JDK-Logging:

    Jar packages required:

    • slf4j-api
    • Slf4j-jdk14 (Integration package)
  • Slf4j integration with log4j1:

    Jar packages required:

    • slf4j-api
    • log4j
    • Slf4j-log4j12 (Integration package)
  • Slf4j integration with log4j2:

    Jar packages required:

    • slf4j-api
    • log4j-api
    • log4j-core
    • Log4j-slf4j-impl (Integration package)
  • Slf4j integration with LogBack:

    Jar packages required:

    • slf4j-api
    • logback-core
    • Logback-classic (Integration Package)
  • Slf4j integration with Commons-logging:

    Jar packages required:

    • slf4j-api
    • commons-logging
    • Slf4j-jcl (Integration Package)

4 Switch between log systems

4.1 Log4J Seamlessly switches to LogBack

4.4.1 case

We have used the log4j1 API in the code to log output, now without changing the existing code to logback to do the actual log output.

Jar packages used:

  • log4j

Use cases:

private static final Logger logger=Logger.getLogger(Log4jTest.class); public static void main(String[] args){ if(logger.isInfoEnabled()){ logger.info("log4j info message"); }}Copy the code

The Logger mentioned above is log4j1’s org.apache.log4j.Logger. In the above code, we are using log4j1 API to program

Now how can the above log output be output through logback?

Just replace the jar package:

  • Step 1: Remove the Log4j JAR package

  • Step 2: Add the following JAR packages

    • Log4j-over-slf4j (switch log4j1 to SLf4j)
    • slf4j-api
    • logback-core
    • logback-classic
  • Step 3: Add the logback configuration file to the classpath

How does that work?

4.1.2 Switching Principle

See log4J-over-slf4j for an example:

As you can see, this is a simplified and improved version of Log4j. Remove log4j1’s native JAR package and replace it with this simplified and improved jar package (which allows seamless migration).

But the implementation of loggers in the simplified version is different from that in the native version. In the simplified version, loggers are implemented as follows (inheriting categories) :

public class Category { private String name; protected org.slf4j.Logger slf4jLogger; private org.slf4j.spi.LocationAwareLogger locationAwareLogger; Category(String name) { this.name = name; slf4jLogger = LoggerFactory.getLogger(name); if (slf4jLogger instanceof LocationAwareLogger) { locationAwareLogger = (LocationAwareLogger) slf4jLogger; }}}Copy the code

As you can see from above, the simplified version of Logger is generated internally using the SLF4J API, so the simplified version of Logger we use will delegate to SLF4J for output. Since logback-classic is in the current classpath, SLF4J will choose Logback for output. Thus log4j to Logback log switch is realized.

The following sections will only cover switching from the logging system to SLF4J, not what kind of logging SLF4J chooses to output

4.2 JDK-logging seamlessly switches to Logback

2 cases

private static final Logger logger=Logger.getLogger(JulSlf4jLog4jTest.class.getName());

public static void main(String[] args){
    logger.log(Level.INFO,"jul info a msg");
    logger.log(Level.WARNING,"jul waring a msg");
}
Copy the code

As you can see, this was programmed using the JDK-Logging API, and now we want to pass the logs to Logback for output

The solutions are as follows:

  • Step 1: Add the following JAR packages:

    • Jul-to-slf4j (implementing JDK-logging switching to SLf4J)
    • slf4j-api
    • logback-core
    • logback-classic
  • Step 2: Add the logback configuration file to the classpath

  • Step 3: Add the following code to your code:

    static{
        SLF4JBridgeHandler.install();
    }
    Copy the code

4.2.2 Switching Principle

Let’s look at the contents of the Jul-to-slf4J JAR package:

We see that there is only one class: SLF4JBridgeHandler

It inherits the JDK – logging defined in Java. Util. Logging. The Handler, Handler is JDK – logging processing log the process of a processor (specific I didn’t also carefully studied), before use, must be registered in advance the processor, Namely the SLF4JBridgeHandler. Install () operation, we can be achieved by the handler after the install log switch work, as follows:

protected Logger getSLF4JLogger(LogRecord record) {
    String name = record.getLoggerName();
    if (name == null) {
        name = UNKNOWN_LOGGER_NAME;
    }
    return LoggerFactory.getLogger(name);
}
Copy the code

In the process of processing logs, slF4J’s native LoggerFactory is used to obtain a Logger defined by SLF4J to output logs

Slf4j, in turn, selects Logback for the actual log output

4.3 Commons-logging switch to logback

4.3.1 Use Cases

Jar package used

  • commons-logging

Examples are as follows:

private static Log logger=LogFactory.getLog(JulJclTest.class); public static void main(String[] args){ if(logger.isTraceEnabled()){ logger.trace("commons-logging-jcl trace message"); }}Copy the code

As you can see, we are using the COMMONs-logging API for logging. Now we want to switch to logback for logging output (this is actually the integration of Commons-logging and logback).

The solutions are as follows:

  • Step 1: Remove the Commons-logging jar package (it doesn’t matter if you go there or not)

  • Step 2: Add the following JAR packages:

    • Jcl-over-slf4j (implementing commons-logging switching to SLf4J)
    • slf4j-api
    • logback-core
    • logback-classic
  • Step 3: Add the logback configuration file to the classpath

4.3.2 Switching principle

This principle has been explained before, as can be seen from commons-logging and logback integration

Commons-logging uses JCL-over-SLf4J to select SLF4J as the underlying logging object, and SLF4J chooses Logback as the underlying logging object.

4.4 Description of Switching log Scenarios

The above log switching principle is clear, the following is for specific examples to apply

Let’s take a look at the official picture of SLF4J:

These three cases are described in detail below

4.4.1 onion parody

  • Status:

    Current applications already use the following hybrid apis for logging programming:

    • commons-logging
    • log4j1
    • jdk-logging

    Now you want to uniformly pass the output of the log to logback

  • Solutions:

    • Step 1: Switch all the logging systems mentioned above to SLF4J seamlessly first

      • Remove commons-logging and switch the underlying logging output to SLf4J using jCL-over-slf4J
      • Remove log4j1(it must be removed) and use log4J-over-slf4j to switch log output from log4j1 to SLf4j
      • Switch the juL log output to SLf4J using jul-to-slf4J
    • Step 2: Make SLF4J select LogBack as the underlying log output

    Add the following JAR packages:

    • slf4j-api
    • logback-core
    • logback-classic

The following two images are similar to the ones above

4.4.2 YouShangTu

  • Status:

    Current applications already use the following hybrid apis for logging programming:

    • commons-logging
    • jdk-logging

    Now you want to uniformly pass the output of the log to log4j1

  • Solutions:

    • Step 1: Switch all the logging systems mentioned above to SLF4J seamlessly first

      • Remove commons-logging and switch the underlying logging output to SLf4J using jCL-over-slf4J
      • Switch the juL log output to SLf4J using jul-to-slf4J
    • Step 2: Make SLF4J select log4j1 as the underlying log output

    Add the following JAR packages:

    • slf4j-api
    • log4j
    • Slf4j-log4j12 (Integration package)

4.4.3 lower left figure

  • Status:

    Current applications already use the following hybrid apis for logging programming:

    • commons-logging
    • log4j

    Now you want to give the log output to JDK-Logging uniformly

  • Solutions:

    • Step 1: Switch all the logging systems mentioned above to SLF4J seamlessly first

      • Remove commons-logging and switch the underlying logging output to SLf4J using jCL-over-slf4J
      • Remove log4j1(it must be removed) and use log4J-over-slf4j to switch log output from log4j1 to SLf4j
    • Step 2: Make SLF4J select JDK-logging as the underlying logging output

    Add the following JAR packages:

    • slf4j-api
    • Slf4j-jdk14 (Integration package)

5 Conflict Description

Still here is the content of the slF4J official website conflict note

In fact, it is easy to understand the function of each JAR package introduced above

5.1 JCL-over-SLf4J conflicts with SLF4J-JCL

  • Jcl-over-slf4j: Commons-logging switches to SLf4J
  • Slf4j-jcl: SLf4J switches to commons-logging

If these two coexist, it will inevitably lead to mutual delegation, resulting in memory overflow

5.2 Log4j-over-slf4j Conflicts with slf4j-log4j12

  • Log4j-over-slf4j: switch log4j1 to slf4j
  • Slf4j-log4j12: SLf4J switches to log4j1

If these two coexist, it will inevitably lead to mutual delegation, resulting in memory overflow. However, log4j-over-slF4 makes an internal judgment to prevent memory overflow:

Namely in judge slf4j – log4j12 jar package org. Slf4j. Impl. Log4jLoggerFactory exists, if the said conflict, throw an exception prompt the user to remove the corresponding jar package, the HTML code is as follows, In slf4j – log4j12 jar package org.. Apache log4j. Log4jLoggerFactory:

5.3 Jul-to-slf4J conflicts with slf4J-JDk14

  • Jul-to-slf4j: JdK-logging switches to SLf4J
  • Slf4j-jdk14: SLf4J switches to JDK-logging

If these two coexist, it will inevitably lead to mutual delegation, resulting in memory overflow

6 the conclusion

At this point, the log series is finally complete. It focuses on the interaction and integration between logging systems, so delving into the architecture of individual logging systems is up to you. From: my.oschina.net/pingpangkua…