巧用 MDC 打出漂亮的日志
介绍
Mapped Diagnostic Context (MDC) 是主流 log 框架自带的功能,将某些信息存在 context 中,然后反映到日志中去。
用的好的话,可以使得日志看起来有条理很多。
背景
一个 batch processing 的应用,每个批次都有一个特定的 DATASET ID。想要(跨多个文件)打出如下的日志:
08:30:00.100 [DATASET 123456] INFO this is message 1
08:30:00.200 [DATASET 123456] INFO this is message 2
08:30:00.300 [DATASET 123456] INFO this is message 3
08:30:00.400 [DATASET 123456] INFO this is message 4
08:30:00.500 [DATASET 123456] INFO this is message 5
可以使用Thread.setName
如下:
Thread.currentThread().setName( "DATASET 123456" );
但是,Thread.setName
是比较"重"的操作,有没有什么更轻量的方法呢?
有的,是使用MDC
。
实现
Java 部分代码,使用MDC.put
:
import org.slf4j.MDC;
MDC.put("context", "DATASET 123456");
// some logic
MDC.clear();
日志配置文件(以 logback 为例),加入%X{PUT_HERE_THE_KEY_NAME}
:
<encoder>
<pattern>%d{HH:mm:ss.SSS} [%X{context}] %-5level %logger{36}.%M\(%line\) - %msg%n</pattern>
</encoder>
注意点
一定,记得用完要清理:clear()
!
否则,多线程的情况下,context 可能被下一个线程使用。(背后,MDC 使用 ThreadLocals 方式实现)
参考
- mdc-in-log4j-2-logback https://www.baeldung.com/mdc-in-log4j-2-logback