Log4j2.properties配置Rewrite Policy不生效问题求助
Log4j2 Properties配置Rewrite Policy掩码不生效问题修复
问题背景
需要通过Log4j2的Rewrite Policy实现日志字段掩码,已找到XML格式的可行配置,但切换到log4j2.properties后Rewrite功能未生效。自定义RewritePolicy函数本身运行正常,但日志文件中无掩码效果。
参考的XML配置(可行)
<Configuration status="warn" name="MyApp" packages=""> <Properties> <Property name="LOG_DIR">/logs</Property> </Properties> <Appenders> <RollingFile name="rollingFile" fileName="D:/logs/omnichannel/application.log" filePattern="D:/logs/omnichannel/application.%i.log.gz" ignoreExceptions="false"> <PatternLayout> <Pattern>%d{yyyy-MM-dd HH:mm:ss} %-5p %m%n</Pattern> </PatternLayout> <Policies> <SizeBasedTriggeringPolicy size="10MB" /> </Policies> <DefaultRolloverStrategy max="5"> <Delete basePath="D:/logs/" maxDepth="2"> <IfFileName glob="*/app-*.log.gz" /> <IfLastModified age="P30D" /> </Delete> </DefaultRolloverStrategy> </RollingFile> <Console name="STDOUT" target="SYSTEM_OUT" ignoreExceptions="false"> <PatternLayout pattern="%m%n"/> </Console> <Rewrite name="Rewrite"> <LogInterceptor /> <AppenderRef ref="rollingFile"/> </Rewrite> </Appenders> <Loggers> <Root level="info"> <AppenderRef ref="Rewrite"/> </Root> </Loggers> </Configuration>
我的log4j2.properties配置(未生效)
status = warn name= PropertiesConfig # Give directory path where log files should get stored property.basePath = D://logs// appenders = rolling, console, Rewrite appender.Rewrite.type = Rewrite appender.Rewrite.name = Rewrite appender.Rewrite.layout.type = LogInterceptor appender.Rewrite.layout.RewriteAppender = fileLogger # ConsoleAppender will print logs on console appender.console.type = Console appender.console.name = consoleLogger appender.console.target = SYSTEM_OUT appender.console.layout.type = PatternLayout # Specify the pattern of the logs appender.console.layout.pattern = %d{yyyy-MM-dd HH:mm:ss.SSS} [%thread] %highlight{[%-5level]}{TRACE=magenta} %mask %logger{36}.%M(%L) : %msg%n%throwable appender.console.layout.disableAnsi=false # RollingFileAppender will print logs in file which can be rotated based on time or size appender.rolling.type = RollingFile appender.rolling.name = fileLogger appender.rolling.fileName = ${basePath}${hostName}.log appender.rolling.filePattern = ${basePath}${hostName}_%d{yyyy-MM-dd}-%i.log.gz appender.rolling.layout.type = PatternLayout appender.rolling.layout.pattern = %d{yyyy-MM-dd HH:mm:ss.SSS} [%thread] [%-5level] %logger{36}.%M(%L) : %msg%n%throwable appender.rolling.policies.type = Policies # Rotate log file each day and keep 30 days worth appender.rolling.policies.time.type = TimeBasedTriggeringPolicy appender.rolling.policies.time.interval = 1 appender.rolling.strategy.type = DefaultRolloverStrategy appender.rolling.strategy.action.type = Delete appender.rolling.strategy.action.basePath = ${basePath} appender.rolling.strategy.action.maxDepth = 1 appender.rolling.strategy.action.ifLastModified.type = IfLastModified appender.rolling.strategy.fileIndex = nomax # For hibernate tracing query parameter, make this default not opened #loggers = application, hibernate loggers = application, httpclient, Client # Mention package name here. Classes in this package or sub packages will use ConsoleAppender and RollingFileAppender for logging logger.application.name = com.project logger.application.level = info logger.application.appenderRefs = rolling logger.application.appenderRef.rolling.ref = fileLogger logger.httpclient.name = org.apache.http logger.httpclient.level = info logger.httpclient.appenderRefs = rolling logger.httpclient.appenderRef.rolling.ref = fileLogger logger.Client.name = com.sun.jersey.api logger.Client.level = info logger.Client.appenderRefs = rolling logger.Client.appenderRef.rolling.ref = fileLogger # For hibernate tracing query parameter, make this default not opened #logger.hibernate.name = org.hibernate.type #logger.hibernate.level = trace #Logger.hibernate.Additivity = false # Configure root logger for logging error logs in classes which are in package other than above specified package rootLogger.level = info rootLogger.appenderRefs = Rewrite rootLogger.appenderRef.Rewrite.ref = Rewrite
自定义RewritePolicy实现
@Plugin(name = "LogInterceptor", category = "Core", elementType = "rewritePolicy", printObject = true) public class LoggingMaskingConverter implements RewritePolicy { protected static final Logger log = LogManager.getLogger(LoggingMaskingConverter.class); private static final List<String> loggingSetting = Arrays.asList("pin,password".split(",")); private static final String loggingMasking = "1"; private static final List<String> excludePath = Collections.emptyList(); private static final String STR_BODY = "body=["; Properties prop = new Properties(); @PluginFactory public static LoggingMaskingConverter createPolicy() { return new LoggingMaskingConverter(); } @Override public LogEvent rewrite(LogEvent event) { if (event.getLoggerName().contains("com.project")) { Message outputMessage = logInfoMasking(event.getMessage()); return new Log4jLogEvent.Builder(event).setMessage(outputMessage).build(); } else { return new Log4jLogEvent.Builder(event).build(); } } public Message logInfoMasking(Message message) { StringBuilder stringBuilder = new StringBuilder(); try { String body = message.getFormattedMessage(); ObjectWriter ow = new ObjectMapper().writer().withDefaultPrettyPrinter(); if (StringUtils.isNotBlank(loggingMasking) && loggingMasking.equalsIgnoreCase("1")) { if (body != null) { Collection<String> whitelist = loggingSetting; Collection<String> excludeKeys = excludePath; JsonMasker masker = new JsonMasker(whitelist, excludeKeys); JsonNode jsonNode = new ObjectMapper().readTree(body); JsonNode masked = masker.mask(jsonNode); stringBuilder.append(STR_BODY + masked.toString() + "]"); } } else { String json = ow.writeValueAsString(body); stringBuilder.append(STR_BODY + json + "]"); } } catch (JsonProcessingException e) { log.error(e, e); } return new ObjectMessage(stringBuilder.toString()); } }
修复方案
1. 修正Rewrite Appender配置
原配置错误使用layout绑定RewritePolicy,且目标Appender配置方式有误,替换为以下配置:
appender.Rewrite.type = Rewrite appender.Rewrite.name = Rewrite # 绑定自定义RewritePolicy插件 appender.Rewrite.policy.type = LogInterceptor # 指定Rewrite后要转发的目标Appender appender.Rewrite.appenderRefs = fileLogger appender.Rewrite.appenderRef.fileLogger.ref = fileLogger
2. 让自定义Logger通过Rewrite处理
原自定义Logger直接关联fileLogger,绕过了Rewrite,需修改为指向Rewrite Appender:
logger.application.name = com.project logger.application.level = info logger.application.appenderRefs = Rewrite logger.application.appenderRef.Rewrite.ref = Rewrite logger.httpclient.name = org.apache.http logger.httpclient.level = info logger.httpclient.appenderRefs = Rewrite logger.httpclient.appenderRef.Rewrite.ref = Rewrite logger.Client.name = com.sun.jersey.api logger.Client.level = info logger.Client.appenderRefs = Rewrite logger.Client.appenderRef.Rewrite.ref = Rewrite
3. 可选:控制台日志也启用掩码
若需要控制台日志也被掩码,修改Rewrite的AppenderRefs同时包含控制台:
appender.Rewrite.appenderRefs = fileLogger, consoleLogger appender.Rewrite.appenderRef.fileLogger.ref = fileLogger appender.Rewrite.appenderRef.consoleLogger.ref = consoleLogger
4. 验证插件加载
确保Log4j2能扫描到自定义插件,可在配置开头添加packages属性指定插件所在包:
packages = com.your.package.path
(替换为LoggingMaskingConverter类所在的包路径)
5. 开启调试日志排查
临时将status = debug,查看Log4j2启动日志,确认:
LogInterceptor插件是否被成功加载- Rewrite Appender是否正确初始化并关联了目标Appender
内容的提问来源于stack exchange,提问作者Fernando Alexsandro Siregar
相关产品推荐
相关产品推荐

