1.创建Appender;
2.logger实例和appender的绑定和解绑
<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-appenderMap<String, Appender> appenders = logger.getAppenders();Appender appender = appenders.get(sessionId);if (appender == null) {// 创建新的RollingFileAppenderappender = RollingFileAppender.newBuilder().setName(sessionId).setLayout(layout).withFileName(fileName).withFilePattern(filePattern).withPolicy(triggeringPolicy).withStrategy(rolloverStrategy).build();// 启动Appenderappender.start();// logger绑定Appenderlogger.addAppender(appender);}}/*** Logger实例解绑Appender* 该方法用于从Logger实例中解绑特定的Appender* 主要目的是在不需要保留日志输出的会话结束时,停止与该会话关联的Appender,并从Logger中移除** @param logger Logger实例,即需要操作的日志记录器* @param sessionId 会话ID,用于标识特定的Appender*/public static void removeLoggerForSession(Logger logger, String sessionId) {// 获取Logger实例中的所有AppenderMap<String, Appender> appenderMap = logger.getAppenders();// 根据会话ID获取对应的AppenderAppender appender = appenderMap.get(sessionId);// 检查是否找到了对应的Appenderif (appender != null) {// 停止Appender,准备解绑appender.stop();// 从Logger实例中移除该Appenderlogger.removeAppender(appender);}}
}