SLF4J, JCL, Jul, log4j1, log4j2, Logback big Summary

Source: Internet
Author: User

1 Series Catalogue
    • Jdk-logging, LOG4J, Logback Journal Introduction and Principle
    • Integration principle of commons-logging and jdk-logging, Log4j1, Log4j2 and Logback
    • Integration principle of slf4j and jdk-logging, Log4j1, Log4j2 and Logback
    • SLF4J, JCL, Jul, log4j1, log4j2, Logback big Summary
2 Summary of various JAR packages
  • LOG4J1:

    • The full contents of log4j:log4j1
  • LOG4J2:

    • API defined by LOG4J-API:LOG4J2
    • LOG4J-CORE:LOG4J2 implementation of the above API
  • Logback:

    • Logback-core:logback's core package
    • Logback-classic:logback implements the SLF4J API
  • Commons-logging:

    • Commons-logging:commons-logging's native content
    • Log4j-jcl:commons-logging to the Log4j2 bridge
    • Jcl-over-slf4j:commons-logging to the SLF4J bridge
  • SLF4J to an actual log frame:

    Scenario Description: Like using SLF4J API for programming, the underlying want to use LOG4J1 to do the actual log output, this is what SLF4J-LOG4J12 do.

    • Slf4j-jdk14:slf4j to the Jdk-logging bridge
    • Slf4j-log4j12:slf4j to the Log4j1 bridge
    • Log4j-slf4j-impl:slf4j to the Log4j2 bridge
    • Logback-classic:slf4j to the Logback bridge
    • Slf4j-jcl:slf4j to the Commons-logging bridge
  • A real log frame turns to slf4j:

    Scenario Description: such as the use of LOG4J1 API programming, but want to eventually through the logback to output, so you need to log4j1 log output to slf4j to output, slf4j again to logback to output. Transfer the output of log4j1 to slf4j, that's what log4j-over-slf4j did.

    This section is used primarily for switching between actual log frames (explained in detail below)

    • Jul-to-slf4j:jdk-logging to the SLF4J bridge
    • Log4j-over-slf4j:log4j1 to the SLF4J bridge
    • Jcl-over-slf4j:commons-logging to the SLF4J bridge
3 Integration Summary3.1 commons-logging integration with other log frameworks
    • 1 commons-logging integration with jdk-logging:

      Required JAR Packages:

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

      Required JAR Packages:

      • Commons-logging
      • Log4j
    • 3 commons-logging integration with LOG4J2:

      Required JAR Packages:

      • Commons-logging
      • Log4j-api
      • Log4j-core
      • LOG4J-JCL (Integration Pack)
    • 4 commons-logging integration with Logback:

      Required JAR Packages:

      • Logback-core
      • Logback-classic
      • Slf4j-api, JCL-OVER-SLF4J (2 integration packs, can no longer need commons-logging)
    • 5 commons-logging integration with SLF4J:

      Required JAR Packages:

      • JCL-OVER-SLF4J (Integration pack, no longer required commons-logging)
      • Slf4j-api
3.2 slf4j integration with other log frameworks
    • SLF4J Integration with jdk-logging:

      Required JAR Packages:

      • Slf4j-api
      • SLF4J-JDK14 (Integration Pack)
    • SLF4J Integration with LOG4J1:

      Required JAR Packages:

      • Slf4j-api
      • Log4j
      • SLF4J-LOG4J12 (Integration Pack)
    • SLF4J Integration with LOG4J2:

      Required JAR Packages:

      • Slf4j-api
      • Log4j-api
      • Log4j-core
      • Log4j-slf4j-impl (Integration Pack)
    • SLF4J Integration with Logback:

      Required JAR Packages:

      • Slf4j-api
      • Logback-core
      • Logback-classic (Integration Pack)
    • SLF4J Integration with commons-logging:

      Required JAR Packages:

      • Slf4j-api
      • Commons-logging
      • SLF4J-JCL (Integration Pack)
4th Switching between log systems4.1 log4j Seamless Switch to Logback4.1.1 Case

We have used the LOG4J1 API in our code for the output of the log, and now we want to make the actual log output through Logback without changing the existing code.

Used jar Packages:

    • Log4j

Use case:

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

The above Logger is log4j1 own Org.apache.log4j.Logger, in the above code, we are using the LOG4J1 API to program

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

Just change the jar package to:

    • First step: Remove the log4j jar package

    • Step Two: Add the following jar packages

      • LOG4J-OVER-SLF4J (implement LOG4J1 switch to SLF4J)
      • Slf4j-api
      • Logback-core
      • Logback-classic
    • Step three: Add the Logback configuration file under the Classpath

What is the principle?

4.1.2 Switching principle

Look at the log4j-over-slf4j at a glance:

As we can see, this is actually a simplified version of the log4j. Remove the native jar package from the log4j1 and replace it with this streamlined version of the jar package (which allows for seamless migration).

However, the implementation in logger and native versions in the simplified version is different, and the logger implementation in the simplified version is as follows (inherited category):

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;        }    }}

From the above can be seen in the simplified version of the logger inside is the use of SLF4J API to generate, so we use a simplified version of the logger will be delegated to slf4j to do the output, because the current class path has Logback-classic, So slf4j will choose logback for output. This enables log switching from log4j to Logback.

The following content will only explain the log system to SLF4J switch, no longer explain SLF4J select which log to output

4.2 jdk-logging Seamless Switch to Logback4.2.1 Case
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");}

You can see that the above is programmed using Jdk-logging's own API, and now we want these logs to be given to Logback to output

The solution is as follows:

    • First step: Add the following jar packages:

      • JUL-TO-SLF4J (implement jdk-logging switch to SLF4J)
      • Slf4j-api
      • Logback-core
      • Logback-classic
    • Step Two: Add the Logback configuration file under the Classpath

    • Step Three: Add the following code to the code:

      static{    SLF4JBridgeHandler.install();}
4.2.2 Switching principle

First look at the contents of the JUL-TO-SLF4J jar package:

We see only one class: Slf4jbridgehandler

It inherits the jdk-logging defined in the Java.util.logging.handler,handler is a processor in the process of jdk-logging processing the log (I have not studied it carefully), before use, you must register the processor in advance, that is, the above Slf4jbri Dgehandler.install () operation, after install we can through this handler to achieve log switching work, as follows:

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

In the process of processing the log, slf4j native mode loggerfactory was used to obtain a slf4j defined logger for the output of the log

And SLF4J will choose Logback to do the actual log output

4.3 commons-logging switch to Logback4.3.1 Use Cases

The jar package used

    • Commons-logging

The cases 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");    }}   

You can see that we use the Commons-logging API to do the log programming operation, now want to switch to Logback to log output (this is actually commons-logging and logback integration)

The solution is as follows:

    • Step one: Remove the commons-logging jar pack (It doesn't matter if you go or not)

    • Step Two: Add the following jar packages:

      • JCL-OVER-SLF4J (implement commons-logging switch to SLF4J)
      • Slf4j-api
      • Logback-core
      • Logback-classic
    • Step three: Add the Logback configuration file under the Classpath

4.3.2 Switching principle

This principle has been said before, you can see the integration of commons-logging and Logback

Commons-logging is to select SLF4J as the underlying log output object through JCL-OVER-SLF4J, and SLF4J chooses Logback as the underlying log output object.

4.4 Common Log Scene switching explanations

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

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

Each of the three cases is described in detail below

4.4.1 Left
    • Present situation:

      The following mixed-mode APIs have been used in the current application to program the log:

      • Commons-logging
      • Log4j1
      • Jdk-logging

      Now want to unify the output of the log to Logback

    • Workaround:

      • First step: Seamlessly switch all of the above log systems to SLF4J first

        • Remove commons-logging (you can not go anywhere), use JCL-OVER-SLF4J to switch commons-logging's underlying log output to SLF4J
        • Remove log4j1 (must be removed), use log4j-over-slf4j to switch log4j1 log output to SLF4J
        • Use JUL-TO-SLF4J to switch the log output of Jul to slf4j
      • Step Two: Make SLF4J select Logback as the underlying log output

      Add the following jar packages:

      • Slf4j-api
      • Logback-core
      • Logback-classic

The following 2 graphs are similar to the one above

4.4.2 Right
    • Present situation:

      The following mixed-mode APIs have been used in the current application to program the log:

      • Commons-logging
      • Jdk-logging

      Now want to unify the output of the log to Log4j1

    • Workaround:

      • First step: Seamlessly switch all of the above log systems to SLF4J first

        • Remove commons-logging (you can not go anywhere), use JCL-OVER-SLF4J to switch commons-logging's underlying log output to SLF4J
        • Use JUL-TO-SLF4J to switch the log output of Jul to slf4j
      • Step Two: Make SLF4J select Log4j1 as the underlying log output

      Add the following jar packages:

      • Slf4j-api
      • Log4j
      • SLF4J-LOG4J12 (Integration Pack)
4.4.3 Left
    • Present situation:

      The following mixed-mode APIs have been used in the current application to program the log:

      • Commons-logging
      • Log4j

      Now want to unify the output of the log to jdk-logging

    • Workaround:

      • First step: Seamlessly switch all of the above log systems to SLF4J first

        • Remove commons-logging (you can not go anywhere), use JCL-OVER-SLF4J to switch commons-logging's underlying log output to SLF4J
        • Remove log4j1 (must be removed), use log4j-over-slf4j to switch log4j1 log output to SLF4J
      • Step Two: Make SLF4J select Jdk-logging as the underlying log output

      Add the following jar packages:

      • Slf4j-api
      • SLF4J-JDK14 (Integration Pack)
5 Conflict Notes

is still the content here slf4j official website conflict explanation

In fact, it is easy to understand the role of each jar package described above.

5.1 jcl-over-slf4j and SLF4J-JCL conflict
    • jcl-over-slf4j:commons-logging Switch to SLF4J

    • SLF4J-JCL:SLF4J Switch to Commons-logging

If the two coexist, it will inevitably lead to mutual delegation, causing memory overflow

5.2 Log4j-over-slf4j and SLF4J-LOG4J12 conflict
    • LOG4J-OVER-SLF4J:LOG4J1 Switch to SLF4J
    • SLF4J-LOG4J12:SLF4J Switch to Log4j1

If the two coexist, it will inevitably lead to mutual delegation, causing memory overflow. But the LOG4J-OVER-SLF4 internal makes a judgment that can prevent memory overflow:

That is, determine whether the org.slf4j.impl.Log4jLoggerFactory in the Slf4j-log4j12 jar package exists, if there is a conflict, throw an exception prompts the user to remove the corresponding jar package, the code is as follows, in the SLF4J-LOG4J12 In the org.apache.log4j.Log4jLoggerFactory of the jar package:

5.3 jul-to-slf4j and Slf4j-jdk14 conflict
    • jul-to-slf4j:jdk-logging Switch to SLF4J
    • SLF4J-JDK14:SLF4J Switch to Jdk-logging

If the two coexist, it will inevitably lead to mutual delegation, causing memory overflow

6 concluding remarks

At this point, the log series is finally finished. It focuses on the interaction and integration of the log system, so you want to delve into the architecture of a single log system, you need to go deep into the study.

SLF4J, JCL, Jul, log4j1, log4j2, Logback big Summary

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.