Java 如何在Logback中设置类似MDC的变量,但对于整个应用程序/JVM?
我想在我的日志文件中有一个应用程序记录某些内容的指示器。这意味着整个应用程序的变量相同,但应用程序实例之间的变量不同。为此,我尝试使用MDC,希望如果我直接在main方法中设置它,该变量将被新生成的线程接管。这在使用log4j时或多或少是可行的,但在使用logback时根本不起作用。我知道您可以在日志文件中显示系统变量,但可能有多个应用程序实例在同一台机器上运行,因此这不起作用。那么,我应该如何将这个变量发送到日志文件中呢?我将使用JVM系统属性。当JVM启动时,您可以使用标记Java 如何在Logback中设置类似MDC的变量,但对于整个应用程序/JVM?,java,logback,Java,Logback,我想在我的日志文件中有一个应用程序记录某些内容的指示器。这意味着整个应用程序的变量相同,但应用程序实例之间的变量不同。为此,我尝试使用MDC,希望如果我直接在main方法中设置它,该变量将被新生成的线程接管。这在使用log4j时或多或少是可行的,但在使用logback时根本不起作用。我知道您可以在日志文件中显示系统变量,但可能有多个应用程序实例在同一台机器上运行,因此这不起作用。那么,我应该如何将这个变量发送到日志文件中呢?我将使用JVM系统属性。当JVM启动时,您可以使用标记-Dthings.
-Dthings.that.arent.bacon=turkey bacon
,或通过编程方式设置每个进程的属性:System.setProperty(“no.not.what.they.tell.You”,“turkey bacon不是bacon”)代码>
如果您使用的是SLF4J/LogBack,则LogBack中似乎已经支持此功能:我认为不可能为整个应用程序设置MDC变量
我正在做的是扩展我想要的appender,以静态方式设置所需的参数,并为每次调用受保护的void append(ILOGingEvent eventObject)方法设置它。这是我的套接字附加器示例:
package my.package
import org.slf4j.MDC;
import java.util.ResourceBundle;
import ch.qos.logback.classic.net.SocketAppender;
import ch.qos.logback.classic.spi.ILoggingEvent;
import ch.qos.logback.classic.spi.LoggingEvent;
public class MyLogbackSocketAppenderWithMDCEnabled extends SocketAppender {
/**
* Example parameter calculated
* This is a list of public IPs of the server
*/
private static final String public_ips = MyNetUtility.getPublicIps();
/**
* Example parameter extracted from a .properties
*
**/
private static final String versio;
static {
String versioAux = null;
try {
final ResourceBundle app = ResourceBundle.getBundle("application");
versioAux = app.getString("versio");
} catch (final Exception e) {
; /*If we have problems loading the bundle, versio=null*/
}
versio = versioAux;
}
@Override
protected void append(ILoggingEvent eventObject) {
if (eventObject instanceof LoggingEvent) {
/*Setting of the parameters in the MDC*/
MDC.put("public_ips", public_ips);
if (versio != null) {
MDC.put("versio", versio);
}
final LoggingEvent loggingEvent = ((LoggingEvent) eventObject);
/* This loads the MDC in the event */
loggingEvent.getMDCPropertyMap();
}
super.append(eventObject);
}
}
然后我在logback.xml中使用它,就像普通的SocketAppender一样,具有相同的配置属性:
<appender name="SOCKET" class="my.package.MyLogbackSocketAppenderWithMDCEnabled">
<remoteHost>${logger.host}</remoteHost>
<port>${logger.port}</port>
<reconnectionDelay>10000</reconnectionDelay>
<includeCallerData>false</includeCallerData>
</appender>
${logger.host}
${logger.port}
10000
假的
也许这不是一个干净的解决方案,但它是有效的。属性的定义是您要搜索的吗
您可以定义属性
并在模式%-5级属性{APP_INSTANCE}[%thread]:%message%n
中使用它。看
如果需要,可以先检查属性是否存在:
<if condition='isDefined("APP_INSTANCE")'>
<then>
...
</then>
</if>
...
这似乎适用于像我正在写入的文件这样的配置,但如何在日志模式本身中使用它?如果所需的属性只能从应用程序内部访问(例如使用打包在其中的.property文件),该怎么办或者,如果我们没有修改启动参数的权限,您可以在模式中使用property关键字。