log4j

Log4j2的日志输出过程

2021-02-21  本文已影响0人  晴天哥_王志

系列

背景

 该篇文章主要介绍Log4j2的日志输出过程,核心流程包含获取Logger对象和通过Logger输出日志。

Logger获取过程

Log4j2获取Logger的过程主要从LoggerContext、LoggerRegistry处获取Logger对象。

public class LogManager {

    public static Logger getLogger(final String name) {
        return name != null ? getContext(false).getLogger(name) : 
                   getLogger(StackLocatorUtil.getCallerClass(2));
    }
}
public class LoggerContext

    public Logger getLogger(final String name, final MessageFactory messageFactory) {

        // 通过LoggerRegistry来获取Logger对象
        Logger logger = loggerRegistry.getLogger(name, messageFactory);
        if (logger != null) {
            AbstractLogger.checkMessageFactory(logger, messageFactory);
            return logger;
        }

        logger = newInstance(this, name, messageFactory);
        loggerRegistry.putIfAbsent(name, messageFactory, logger);
        return loggerRegistry.getLogger(name, messageFactory);
    }
}
public class LoggerRegistry<T extends ExtendedLogger> {

    public T getLogger(final String name, final MessageFactory messageFactory) {
        return getOrCreateInnerMap(factoryKey(messageFactory)).get(name);
    }

    private Map<String, T> getOrCreateInnerMap(final String factoryName) {
        Map<String, T> inner = map.get(factoryName);
        if (inner == null) {
            inner = factory.createInnerMap();
            map.put(factoryName, inner);
        }
        return inner;
    }
}

日志输出过程

日志输出源码

public abstract class AbstractLogger

    public void logIfEnabled(final String fqcn, final Level level, final Marker marker, final String message,final Throwable t) {
        // 全局Filter和全局的日志级别进行过滤
        if (isEnabled(level, marker, message, t)) {
            // 输出日志
            logMessage(fqcn, level, marker, message, t);
        }
    }

    protected void logMessage(final String fqcn, final Level level, 
          final Marker marker, final String message,final Throwable t) {
        // 通过ReusableMessageFactory组建消息体
        logMessageSafely(fqcn, level, marker, 
                 messageFactory.newMessage(message), t);
    }

    private void logMessageSafely(final String fqcn, final Level level, 
           final Marker marker, final Message msg, final Throwable throwable) {
        try {
            logMessageTrackRecursion(fqcn, level, marker, msg, throwable);
        } finally {
            ReusableMessageFactory.release(msg);
        }
    }

    private void logMessageTrackRecursion(final String fqcn,
                                          final Level level,
                                          final Marker marker,
                                          final Message msg,
                                          final Throwable throwable) {
        try {
            incrementRecursionDepth(); // LOG4J2-1518, LOG4J2-2031
            tryLogMessage(fqcn, getLocation(fqcn), level, 
                           marker, msg, throwable);
        } finally {
            decrementRecursionDepth();
        }
    }

    private void tryLogMessage(final String fqcn,
                               final StackTraceElement location,
                               final Level level,
                               final Marker marker,
                               final Message msg,
                               final Throwable throwable) {
        try {
            log(level, marker, fqcn, location, msg, throwable);
        } catch (final Exception e) {
            handleLogMessageException(e, fqcn, msg);
        }
    }

    protected void log(final Level level, final Marker marker, 
                  final String fqcn, final StackTraceElement location,
                  final Message message, final Throwable throwable) {
        // strategy为AwaitCompletionReliabilityStrategy
        final ReliabilityStrategy strategy = 
             privateConfig.loggerConfig.getReliabilityStrategy();
        if (strategy instanceof LocationAwareReliabilityStrategy) {
            // 继续跟进log过程
            ((LocationAwareReliabilityStrategy) strategy)
              .log(this, getName(), fqcn, location, marker, level,
                     message, throwable);
        } else {
            // 省略代码
        }
    }
}
public class Logger extends AbstractLogger implements Supplier<LoggerConfig> {

    public boolean isEnabled(final Level level, final Marker marker, 
                               final String message, final Throwable t) {
        return privateConfig.filter(level, marker, message, t);
    }

    protected class PrivateConfig {
        boolean filter(final Level level, final Marker marker, 
                            final String msg, final Throwable t) {
            // 先通过全局的Filter进行过滤
            final Filter filter = config.getFilter();
            if (filter != null) {
                final Filter.Result r = 
                      filter.filter(logger, level, marker, (Object) msg, t);
                if (r != Filter.Result.NEUTRAL) {
                    return r == Filter.Result.ACCEPT;
                }
            }
            // 再判断日志等级是否满足要求
            return level != null && intLevel >= level.intLevel();
        }
    }
}
public class AwaitCompletionReliabilityStrategy 

    public void log(final Supplier<LoggerConfig> reconfigured, 
        final String loggerName, final String fqcn,
        final StackTraceElement location, final Marker marker, 
        final Level level, final Message data, final Throwable t) {

        // 通过LoggerConfig的进行日志打印
        final LoggerConfig config = getActiveLoggerConfig(reconfigured);
        try {
            config.log(loggerName, fqcn, location, marker, level, data, t);
        } finally {
            config.getReliabilityStrategy().afterLogEvent();
        }
    }
}
public class LoggerConfig extends AbstractFilterable implements LocationAware {

    public void log(final String loggerName, final String fqcn, 
        final StackTraceElement location, final Marker marker,
        final Level level, final Message data, final Throwable t) {
        List<Property> props = null;
        if (!propertiesRequireLookup) {
            props = properties;
        } 

        // 创建LogEvent对象
        final LogEvent logEvent = 
         logEventFactory instanceof LocationAwareLogEventFactory ?
            ((LocationAwareLogEventFactory) logEventFactory).createEvent(
                loggerName, marker, fqcn, location, level, data, props, t) : 
           logEventFactory.createEvent(
            loggerName, marker, fqcn, level, data, props, t);

        try {
            // 继续执行
            log(logEvent, LoggerConfigPredicate.ALL);
        } finally {
            ReusableLogEventFactory.release(logEvent);
        }
    }

    protected void log(final LogEvent event, 
                 final LoggerConfigPredicate predicate) {
        if (!isFiltered(event)) {
            processLogEvent(event, predicate);
        }
    }

    private void processLogEvent(final LogEvent event, 
                    final LoggerConfigPredicate predicate) {
        event.setIncludeLocation(isIncludeLocation());
        if (predicate.allow(this)) {
            callAppenders(event);
        }
        logParent(event, predicate);
    }

    protected void callAppenders(final LogEvent event) {
        final AppenderControl[] controls = appenders.get();
        //noinspection ForLoopReplaceableByForEach
        for (int i = 0; i < controls.length; i++) {
            controls[i].callAppender(event);
        }
    }
}
public class AppenderControl extends AbstractFilterable {

    public void callAppender(final LogEvent event) {
        if (shouldSkip(event)) {
            return;
        }
        callAppenderPreventRecursion(event);
    }

    private void callAppenderPreventRecursion(final LogEvent event) {
        try {
            recursive.set(this);
            callAppender0(event);
        } finally {
            recursive.set(null);
        }
    }

    private void callAppender0(final LogEvent event) {
        ensureAppenderStarted();
        if (!isFilteredByAppender(event)) {
            tryCallAppender(event);
        }
    }

    private void tryCallAppender(final LogEvent event) {
        try {
            appender.append(event);
        } catch (final RuntimeException ex) {
            handleAppenderError(event, ex);
        } catch (final Exception ex) {
            handleAppenderError(event, new AppenderLoggingException(ex));
        }
    }

    private boolean shouldSkip(final LogEvent event) {
        return isFilteredByAppenderControl(event) 
                  || isFilteredByLevel(event) || isRecursiveCall();
    }
}
public abstract class AbstractOutputStreamAppender<
        M extends OutputStreamManager> extends AbstractAppender {

    public void append(final LogEvent event) {
        try {
            tryAppend(event);
        } catch (final AppenderLoggingException ex) {
            throw ex;
        }
    }

    private void tryAppend(final LogEvent event) {
        if (Constants.ENABLE_DIRECT_ENCODERS) {
            directEncodeEvent(event);
        } else {
            writeByteArrayToManager(event);
        }
    }

    protected void directEncodeEvent(final LogEvent event) {
        getLayout().encode(event, manager);
        if (this.immediateFlush || event.isEndOfBatch()) {
            manager.flush();
        }
    }
}
上一篇 下一篇

猜你喜欢

热点阅读