Java程序运行时动态生成日志文件-loj4j

1.创建Appender;

2.logger实例和appender的绑定和解绑

3.logger实例使用 private static final Logger LOGGER = LogManager.getLogger(DeviceManagerCuppsIOHandler.class); 创建

    <dependency>
        <groupId>org.slf4j</groupId>
        <artifactId>slf4j-api</artifactId>
        <version>1.7.25</version>
    </dependency>
    <dependency>
        <groupId>org.apache.logging.log4j</groupId>
        <artifactId>log4j-core</artifactId>
        <version>2.17.2</version>
    </dependency>
    <dependency>
        <groupId>org.apache.logging.log4j</groupId>
        <artifactId>log4j-slf4j-impl</artifactId>
        <version>2.17.2</version>
    </dependency>
        <!--这个需不需要引入看情况!-->
    <dependency>
        <groupId>org.slf4j</groupId>
        <artifactId>slf4j-nop</artifactId>
        <version>1.7.25</version>
    </dependency>
package com.xx;

import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.core.Appender;
import org.apache.logging.log4j.core.Logger;
import org.apache.logging.log4j.core.LoggerContext;
import org.apache.logging.log4j.core.appender.RollingFileAppender;
import org.apache.logging.log4j.core.appender.rolling.CompositeTriggeringPolicy;
import org.apache.logging.log4j.core.appender.rolling.DefaultRolloverStrategy;
import org.apache.logging.log4j.core.appender.rolling.SizeBasedTriggeringPolicy;
import org.apache.logging.log4j.core.appender.rolling.TimeBasedTriggeringPolicy;
import org.apache.logging.log4j.core.config.Configuration;
import org.apache.logging.log4j.core.layout.PatternLayout;

import java.util.Map;

/**
 *
 * log4j在程序运行时根据sessionId动态创建日志文件
 * <p>
 * .
 *
 * @author little_lunatic
 * @date 2025-01-14
 */
public class DynamicLogging {

    /** 获取Logger上下文 */
    private static final LoggerContext context = (LoggerContext) LogManager.getContext(false);
    /** 创建布局 */
    private static final PatternLayout layout = PatternLayout.newBuilder()
            .withPattern("[#%%&*^]%d{yyyyMMddHHmmss:SSS}.%ip:%processID,%threadID#%X{TransactionID}%%%X{CID}&%X{SessionID}*%X{CWA}^%X{serialNo}:%p>[%logger{0}:%L] %X{minaSessionId}>> %msg%n")
            .build();

    /** 创建TimeBasedTriggeringPolicy和SizeBasedTriggeringPolicy */
    private static final TimeBasedTriggeringPolicy timeBasedTriggeringPolicy = TimeBasedTriggeringPolicy.newBuilder()
            .withInterval(1)
            .withModulate(true)
            .build();
    private static final SizeBasedTriggeringPolicy sizeBasedTriggeringPolicy = SizeBasedTriggeringPolicy.createPolicy("10MB");

    /**使用CompositeTriggeringPolicy组合多个触发策略 */
    private static final CompositeTriggeringPolicy triggeringPolicy = CompositeTriggeringPolicy.createPolicy(timeBasedTriggeringPolicy, sizeBasedTriggeringPolicy);

    /** 创建DefaultRolloverStrategy */
    private static final DefaultRolloverStrategy rolloverStrategy = DefaultRolloverStrategy.newBuilder().withMax("7").build();

    /**
     * Logger实例绑定Appender
     * @param logger 需要绑定Appender的Logger实例
     * @param sessionId 会话ID,用于区分不同的日志文件
     */
    public static void createLoggerForSession(Logger logger, String sessionId) {
        // 从上下文中获取当前配置
        Configuration configuration = context.getConfiguration();

        // 读取属性
        String prefix = configuration.getStrSubstitutor().replace("${LOG_HOME}/${APP_NAME}.${MODULE_NAME}");

        // 定义日志文件名和模式
//        String fileName = prefix + ".session-" + sessionId + ".log";
//        String filePattern = prefix + ".session-" + sessionId + "_%d{yyyy-MM-dd}-%i.log.gz";
        String fileName = "logs/session-" + sessionId + ".log";
        String filePattern = "logs/session-" + sessionId + "_%d{yyyy-MM-dd}-%i.log.gz";

        // 避免未remove之前,多次创建相同的sessionid-appender
        Map<String, Appender> appenders = logger.getAppenders();
        Appender appender = appenders.get(sessionId);
        if (appender == null) {
            // 创建新的RollingFileAppender
            appender = RollingFileAppender.newBuilder()
                    .setName(sessionId)
                    .setLayout(layout)
                    .withFileName(fileName)
                    .withFilePattern(filePattern)
                    .withPolicy(triggeringPolicy)
                    .withStrategy(rolloverStrategy)
                    .build();
            // 启动Appender
            appender.start();
            // logger绑定Appender
            logger.addAppender(appender);
        }
    }

    /**
     * Logger实例解绑Appender
     * 该方法用于从Logger实例中解绑特定的Appender
     * 主要目的是在不需要保留日志输出的会话结束时,停止与该会话关联的Appender,并从Logger中移除
     *
     * @param logger Logger实例,即需要操作的日志记录器
     * @param sessionId 会话ID,用于标识特定的Appender
     */
    public static void removeLoggerForSession(Logger logger, String sessionId) {
        // 获取Logger实例中的所有Appender
        Map<String, Appender> appenderMap = logger.getAppenders();
        // 根据会话ID获取对应的Appender
        Appender appender = appenderMap.get(sessionId);
        // 检查是否找到了对应的Appender
        if (appender != null) {
            // 停止Appender,准备解绑
            appender.stop();
            // 从Logger实例中移除该Appender
            logger.removeAppender(appender);
        }
    }
}

posted @   little_lunatic  阅读(24)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· 震惊!C++程序真的从main开始吗?99%的程序员都答错了
· 【硬核科普】Trae如何「偷看」你的代码?零基础破解AI编程运行原理
· 单元测试从入门到精通
· winform 绘制太阳,地球,月球 运作规律
· 上周热点回顾(3.3-3.9)
点击右上角即可分享
微信分享提示