log4j가 자체 구성에 사용한 파일을 표시하도록 할 수 있습니까?


79

질문

Log4J가 구성에 사용한 파일의 전체 경로를 표시하도록 할 수 있습니까?


배경

나는 log4j와 애증 관계가 있습니다. 좋은시기에는 훌륭하지만 작동하지 않을 때는 디버깅하기 가장 어려운 일 중 하나가 될 수 있습니다. 애플리케이션의 모든 로깅을 관리합니다. 따라서 저는 매뉴얼에 정의 된 로깅과 기본 초기화 절차에 매우 익숙 합니다. 그래도 몇 주마다 로그 기록이 중단되고 문제를 해결 하는많은 시간을 소비 하는 것 같습니다 .

이번에는 심하게 깨졌습니다. 모든 곳의 모든 로그 문이 콘솔에 덤프되고 이유를 알 수 없습니다. 지난주에 내 log4j.xml 파일을 사용한 것과 동일한 코드 기반이 갑자기 다른 구성을 사용하고 있습니다. 명백한 것은 변경되지 않았습니다. 내 유일한 추측은 몇 가지 종속성이 변경되었으며 Maven이 모든 것을 파괴하는 사악한 JAR을 다운로드했다고 의심합니다.

Log4J가 시작할 때 사용하기로 결정한 구성 파일을 알아낼 수만 있다면 이 문제와 대부분의 다른 문제를 쉽게 해결할 수 있습니다.


요약

Log4J에 구성에 사용 된 파일을 인쇄하도록 지시하는 방법이 있습니까? 또는 실행중인 응용 프로그램을 중단하고 디버거를 사용하여이 질문에 답할 수있는 방법이 있습니까 (식을 사용하거나 변수를 검사하여)?


1
배경이 다중 바인딩 문제처럼 들립니다. From slf4j.org/codes.html#multiple_bindings : SLF4J에서 내 보낸 경고는 바로 경고입니다. 여러 바인딩이있는 경우에도 SLF4J는 하나의 로깅 프레임 워크 / 구현을 선택하고 바인딩합니다. SLF4J가 바인딩을 선택하는 방식은 JVM에 의해 결정되며 모든 실제 목적을 위해 무작위로 간주되어야합니다.
newur

답변:


82

예, log4j.debugJVM 시스템 변수에 추가 하기 만하면 됩니다. 예를 들면 :

java -Dlog4j.debug -cp ... some.class.name

Log4j는 다음과 같은 결과를 출력합니다.

log4j: Trying to find [log4j.xml] using context classloader sun.misc.Launcher$AppClassLoader@1f7182c1.  
log4j: Using URL [file:/C:/Users/matt/workspace/projectname/target/test-classes/log4j.xml] for automatic log4j configuration.  
log4j: Preferred configurator class: org.apache.log4j.xml.DOMConfigurator  
log4j: System property is :null  
log4j: Standard DocumentBuilderFactory search succeded.  
log4j: DocumentBuilderFactory is: org.apache.xerces.jaxp.DocumentBuilderFactoryImpl  
log4j: debug attribute= "null".  
log4j: Ignoring debug attribute.  
log4j: reset attribute= "false".  
log4j: Threshold ="null".  
...

참고로 매뉴얼FAQ 를 참조하십시오 .


6
어떤 이유로이 플래그를 설정해도 SLF4J를 사용하기 때문에 내 프로젝트에 영향을 미치지 않습니다. 이유를 알아 보려고했지만 마침내 수동으로 21 개의 구성 파일을 확인했습니다.)
Line

2
log4j2에서 속성이 log4j2.debug로 변경되었으며 구성 파일을 찾는 데 문제를 디버깅하려는 경우 -Dorg.apache.logging.log4j.simplelog.StatusLogger.level = TRACE를 설정해야 할 수도 있습니다.
user2163960

7

저는 Log4J2를 사용하고 있으며 Java 프로그램 내부에서 파일을 얻으려면 이것이 저에게 효과적이었습니다.

LoggerContext lContect = LogManager.getContext();
Field f = lContect.getClass().getDeclaredField("configuration");
f.setAccessible(true);
XmlConfiguration iWantThis = (XmlConfiguration) f.get(lContect);
System.out.println("Config File: " + iWantThis.getName());

1
한편으로는 이것은 정확히 내가 찾고 있던 것이었고 다른 한편으로는 출력에서 ​​구성 파일을 변경해도 효과가 없었습니다. 따라서 Log4J2가 실제로 사용되는지 정말 확실해야합니다. 여기 slf4j.org/codes.html#multiple_bindings에 설명 된대로 다중 바인딩 문제가 발생 했기 때문에 실제 로거는 slf4j-simple이었습니다.
newur

또한 디버거를 사용하고 org.apache.logging.log4j.util.PropertiesUtil의 생성자에 중단 점을 설정했습니다. 여기에 log4j2.component.properties라는 파일이 있고로드됩니다. 첫 번째는 target / test-classes에서, 두 번째는 target / classes에서 두 번째 파일이로드되었고 후자의 속성은 첫 번째 파일에서 속성을 덮어 쓴다는 것을 발견했습니다.
rychu

2

이에 상응하는 log4j 2 <Configuration status="trace">는 구성 파일에 설정됩니다. 그러면 log4j2 구성 파일이로드 된 위치와 log4j2 구성 프로세스의 기타 내부 세부 정보가 표시됩니다. 기본적으로 상태 로거 수준은 WARN이므로 문제가있는 경우에만 알림이 표시됩니다.

구성 파일을 올바르게 찾을 수없는 경우에도 시스템 속성 org.apache.logging.log4j.simplelog.StatusLogger.level을 로 설정하여 log4j2 내부 상태 로깅을 활성화 할 수 있습니다 TRACE.


5
그러나 사용중인 구성 값을 찾으려고하는 경우 활성 상태가 아닐 수있는 구성 값에 추가해도 아무 소용이 없습니다!
Omaha
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.