我想用AOP實現一個日誌記錄概念,但打印日誌時我需要給我自己的方法名稱而不是默認值。在Logback中覆蓋方法名稱(%M轉換說明符)
更新(基於@glitch評論):
我使用
%M
轉換符告訴的logback包括在每個日誌事件的方法名稱。我想回報某些 logback派生方法名稱spicifically;用於由我的AOP連接點發出的日誌事件。
我不想在日誌事件的其他地方寫'實際方法名'我想要使用的方法名稱是正確的,即表示原始方法而不是攔截方法。
我想用AOP實現一個日誌記錄概念,但打印日誌時我需要給我自己的方法名稱而不是默認值。在Logback中覆蓋方法名稱(%M轉換說明符)
更新(基於@glitch評論):
我使用%M
轉換符告訴的logback包括在每個日誌事件的方法名稱。
我想回報某些 logback派生方法名稱spicifically;用於由我的AOP連接點發出的日誌事件。
我不想在日誌事件的其他地方寫'實際方法名'我想要使用的方法名稱是正確的,即表示原始方法而不是攔截方法。
%M
轉換說明符由ch.qos.logback.classic.pattern.MethodOfCallerConverter
實現。實現相當簡單:
public String convert(ILoggingEvent le) {
StackTraceElement[] cda = le.getCallerData();
if (cda != null && cda.length > 0) {
return cda[0].getMethodName();
} else {
return CallerData.NA;
}
}
所以,你可以提供自己的實現。像這樣的事情也許......
public class CustomMethodOfCallerConverter extends ClassicConverter {
public String convert(ILoggingEvent le) {
StackTraceElement[] cda = le.getCallerData();
if (cda != null && cda.length > 0) {
if (le.getMDCPropertyMap().containsKey("CUSTOM_METHOD_NAME_KEY")) {
String methodName = le.getMDCPropertyMap().get("CUSTOM_METHOD_NAME_KEY");
// remove the MDC entry since we are only using MDC to pass the custom method name into this converter
le.getMDCPropertyMap().remove("CUSTOM_METHOD_NAME_KEY");
return methodName;
} else {
return cda[0].getMethodName();
}
} else {
return CallerData.NA;
}
}
}
...它使用MDC
從您的連接點通過實際的方法名。在您的連接點上,您可以在調用記錄器之前放置MDC值,例如
MDC.put("CUSTOM_METHOD_NAME_KEY", pjp.getSignature().getName()));
但是... Logback不提供任何方式讓您聲明自己的自定義轉換器。 Logback使用的轉換器在 ch.qos.logback.classic.PatternLayout
的靜態初始化器中聲明,並且這不可擴展/可覆蓋。所以,我覺得你的選擇是:
在自己的代碼庫,即用自己的logback取代自己MethodOfCallerConverter創建ch.qos.logback.classic.pattern.MethodOfCallerConverter
類。您可以使用的例子,我的上方,並 - 只要你把MDC的CUSTOM_METHOD_NAME_KEY
值調用的記錄之前 - 它會做你想要什麼
繼續使用%M
符,但對於AOP攔截方法添加附加的MDC屬性顯示實際的方法名稱。這會導致Logback方法名稱出現在所有日誌輸出中,同時出現actula方法名稱(如果可用)。例如:
// put the actual method name in MDC
MDC.put("actualMethodName", pjp.getSignature().getName());
// specify your pattern - in logback.xml - to include the actual method name
%d{yyyy-MM-dd HH:mm:ss}|[%thread]|%-5level|%logger{36}|%M%X{actualMethodName:-}|%msg%n
停止使用%M
符和記錄通過MDC所有方法名。這將導致正確的方法名稱出現,但它會要求您在每種方法中更新MDC(這聽起來很尷尬)。例如:
// put the actual method name in MDC
MDC.put("actualMethodName", pjp.getSignature().getName());
// specify your pattern - in logback.xml - to include the actual method name
%d{yyyy-MM-dd HH:mm:ss}|[%thread]|%-5level|%logger{36}|%X{actualMethodName}|%msg%n
謝謝你是一個天才,現在一切都像一個cham –
由於Logback提供沒有註冊自己的'%M'轉換說明符的鉤子,你'擴展'通過模仿它的'MethodOfCallerConverter'進行Logback。這種方法有效,但它不是標準的,可能很脆弱;如果未來的Logback版本更改了「MethodOfCallerConverter」的名稱或命名空間,那麼您也必須更改「MethodOfCallerConverter」的版本。只是要記住一些事情.... – glytching
你指的「默認」,這是否意味着你使用的是'%M'轉換說明在你的logback模式讓的logback推導方法的名字嗎?您是否想將其替換爲所有日誌事件或僅針對選定的日誌事件?是否必須替換它,或者在日誌消息的其他位置寫入其他方法名稱是否足夠? – glytching
我在兩種方式使用日誌記錄,一種是正常的日誌記錄方法和aspectj AOP。對於正常的日誌記錄方法名稱是正確打印,但對於最終的Logger logger = LoggerFactory.getLogger(pjp.getSignature()。getDeclaringTypeName());這個記錄器打印aop方法而不是確切的方法,我使用'ProceedingJoinPoint' –
在這裏我可以得到確切的方法名稱與pjp.getSignature()。getName(),但記錄器需要打印此方法名稱而不是aop方法名稱,如果這不是possbile我可以用這個方法名稱覆蓋%M –