log4j..계속 사용만 해왔지 정리를 한적이 없어서 정리를 해본다.
1. log4j란?
2. log4j 구조
3. log4j level
4. log4j 간단한 예
5. 참고 사이트
[1] log4j 란?
자바 어플리케이션에서 빠르고 효과적으로 로깅 할 수 있도록 도와주는 오픈소스이다.
[2] log4j 구조
log4j는 크게 3가지의 큰 뼈대를 가지고 있다.
(1) Logger(Category : 요녀석은 잘 쓰지 않는다) : logging 메시지를 Appender에 전달.
(2) Appender : 전달된 로깅 메시지를 파일, 콘솔,DB에 저장 할 지 지정하는 역할을 한다.
(3) Layout : Appender가 어디에 출력 할 것인지 결정했다면 어떠한 형식으로 출력을 할 지
출력 layout을 결정
tip. <root> :
[3] log4j level
logging 레벨은 TRACE < DEBUG < INFO < WARN < ERROR and FATAL 이며,
1) FATAL : 가장 크리티컬한 에러가 났을 때 사용.
2) ERROR : 일반 에러가 났을 경우 사용.
3) WARN : 에러는 아니지만 주의할 필요가 있을 때 사용.
4) INFO : 일반 정보를 나타날 때 사용.
5) DEBUG : 일반 정보를 상세히 나타낼 때 사용.
6) TRACE : 가장 레벨이 낮은 단계, 보통 DEBUG로 많이 하며 TRACE는 본적이...;;
debug 레벨로 했다면 INFO~FATAL까지 모두 logging이 되어집니다.
운영모드라면 INFO레벨로 하면 됩니다.
[4] log4j 간단한 예
1) Appender and Layout 설정
<appender name="ACET_CONSOLE" class="org.apache.log4j.ConsoleAppender">
<param name="Target" value="System.out"/>
<param name="Threshold" value="TRACE"/>
<layout class="org.apache.log4j.PatternLayout">
<param name="ConversionPattern" value="[%p][%d{yyyy-MM-dd HH:mm:ss}] [%p] [%c{1}.%M():%L] - %m%n"/>
</layout>
</appender>
2) Logger
<logger name="kr.pe.acet" additivity="false">
<appender-ref ref="ACET_CONSOLE"/>
<level value="DEBUG" />
</logger>
우선 설명을 들어가기전에 기본적인 내용을 알고 가자!
<1> 로그 파일명 설정주기(DatePattern)
위의 예제는 console이라 적용되어있지 않다.
그래서 아래의 내용을 보도록 하자. 언제 파일을 분리시키면 되는가? 하는 설정이다.
<param name="DatePattern" value="%d{yyyy-MM-dd HH:mm:ss.SSS}"/>
<param name="DatePattern" value="'.'yyyy-MM-dd-HH"/>
'.'yyyy-MM : 매달 첫번째날에 로그파일을 변경한다.
'.'yyyy-WW : 매주의 시작시 로그파일을 변경한다.
'.'yyyy-MM-dd : 매일 자정에 로그파일을 변경한다.
'.'yyyy-MM-dd-a : 자정과 정오에 로그파일을 변경한다.
'.'yyyy-MM-dd-HH : 매 시간의 시작마다 로그파일을 변경한다.
'.'yyyy-MM-dd-HH-mm : 매분마다 로그파일을 변경한다.
<2> PatternLayout 포맷
로그를 어떤 포맷으로 남길지 결정한다.
layout에는 HTMLLayout, PatternLayout, SimpleLayout, XMLLayout등이 있으며 PatternLayout이 일반적으로 가장 많이 쓰인다.
[표-1]
형식 |
설명 |
%p | debug, info, warn, error, fatal 등의 priority 가 출력된다. |
%m | 로그내용이 출력됩니다 |
%d | 로깅 이벤트가 발생한 시간을 기록합니다. 포맷은 %d{HH:mm:ss, SSS}, %d{yyyy MMM dd HH:mm:ss, SSS}같은 형태로 사용하며 SimpleDateFormat에 따른 포맷팅을 하면 된다 |
%t | 로그이벤트가 발생된 쓰레드의 이름을 출력합니다. |
%% | % 표시를 출력하기 위해 사용한다. |
%n | 플랫폼 종속적인 개행문자가 출력된다. \r\n 또는 \n 일것이다. |
%c | 카테고리를 표시합니다 예) 카테고리가 a.b.c 처럼 되어있다면 %c{2}는 b.c가 출력됩니다. |
%C | 클래스명을 포시합니다. 예) 클래스구조가 org.apache.xyz.SomeClass 처럼 되어있다면 %C{2}는 xyz.SomeClass 가 출력됩니다 |
%F | 로깅이 발생한 프로그램 파일명을 나타냅니다. |
%l | 로깅이 발생한 caller의 정보를 나타냅니다 |
%L | 로깅이 발생한 caller의 라인수를 나타냅니다 |
%M | 로깅이 발생한 method 이름을 나타냅니다. |
%r | 어플리케이션 시작 이후 부터 로깅이 발생한 시점의 시간(milliseconds) |
%x | 로깅이 발생한 thread와 관련된 NDC(nested diagnostic context)를 출력합니다. |
%X |
로깅이 발생한 thread와 관련된 MDC(mapped diagnostic context)를 출력합니다. |
자! 이제 위의 내용을 분석해보자~~
우선 눈에 들어오는 것은 PatternLayout과 DEBUG, ConsoleAppender 가 있다.
<appender name="ACET_CONSOLE" class="org.apache.log4j.ConsoleAppender">
<param name="Target" value="System.out"/>
<param name="Threshold" value="TRACE"/>
를 보면 Console에 남기는 것이고, Threshold가 TRACE다. Threshold는 이 appender에 명시 된 priority와 같거나 높은 메시지만 로깅을 한다는 뜻이다.
<layout class="org.apache.log4j.PatternLayout">
<param name="ConversionPattern" value="[%p][%d{yyyy-MM-dd HH:mm:ss}] [%p] [%c{1}.%M():%L] - %m%n"/>
</layout>
</appender>
역시나 Conlsoe 출력이며, PatternLayout를 사용하며, ConversionPattern을 사용 한다.
ConversionPattern : the ConversionPattern parameter controls the contents of each line of output inside the log file
위에 명시 된 [표-1]을 보고 분석해보자.
"[%p][%d{yyyy-MM-dd HH:mm:ss}] [%p] [%c{1}.%M():%L] - %m%n"/>
%p : debug, info, warn, error, fatal 등의 priority 가 출력된다.
%d : 로깅 이벤트가 발생한 시간을 기록합니다.
포맷은 %d{HH:mm:ss, SSS}, %d{yyyy MMM dd HH:mm:ss, SSS}같은 형태로
사용하며 SimpleDateFormat에 따른 포맷팅을 하면 된다
%c : 카테고리를 표시합니다 예) 카테고리가 a.b.c 처럼 되어있다면 %c{2}는 b.c가 출력됩니다.
위의 예제는 %c{1} 이므로 전체가 출력 된다.
%M : 로깅이 발생한 method 이름을 나타냅니다.
%L : 로깅이 발생한 caller의 라인수를 나타냅니다
%m : 로그내용이 출력됩니다
%n : 플랫폼 종속적인 개행문자가 출력된다. \r\n 또는 \n 일것이다.
ex) [DEBUG][2014-01-09 14:42:03] [DEBUG] [DispatcherServlet.init():136] - Servlet
'spring' configured successfully
[5] 참고 사이트
1) http://logging.apache.org/log4j/1.2/apidocs/org/apache/log4j/PatternLayout.html
2) http://logging.apache.org/log4j/2.x/manual/architecture.html // log4j 아키텍처 그림 있음!
[6] 알아두면 좋은 Tip
1) log4j1.2까지는 문제가 없으나 1.3부터는 category가 logger 태그로 흡수 되고, priority 태그가
deprecated 취급을 하니 가능하면 logger, level 태그를 사용하는게 좋다.
2) 아래의 내용은 어떻게 찍힐까??
<logger name="kr.pe.acet">
<level value="INFO" />
<appender-ref ref="ACET_CONSOLE" />
</logger>
<root>
<level value="DEBUG" />
<appender-ref ref="ACET_CONSOLE" />
</root>
root 카테고리에 DEBUG 레벨을 설정했으니, DEBUG 메시지도 출력되는게 맞는것이 아닌가하고 착각을 할 수 있는데, 설정한 logger(kr.pe.acet)의 로그 레벨이 INFO이므로, INFO 메시지까지만 출력이 된다. 즉, 해당 카테고리의 로그 레벨이 설정되어 있으면 그 로그 레벨을 따라간다는것이다.
(참조사이트 : http://blog.kangwoo.kr/54)
3) http://sourceforge.net/p/mindtreeinsight/code/HEAD/tree/
log를 보는 툴인 것 같다. 깔아서 사용은 하지 않았지만..소스를 받아서 분석은 하고 싶네요^^
추가 Tip
ex) <logger name="kr.pe.acet.dev" additivity="false">
부모격의 "kr.pr.acet" 의 logger로 설정이 되어있으면 중복으로 찍히는데 additivity의 옵션을 false로
주면 중복으로 찍히지 않는다.
출처 : http://aircook.tistory.com/entry/log4j%EC%9D%98-additivity-%EC%98%B5%EC%85%98
< 끝 >