1cm

자바 프로그래밍_Day_100_Framework : MyBatis 정리 / log4j 본문

국비지원_Java/Java Programming_2

자바 프로그래밍_Day_100_Framework : MyBatis 정리 / log4j

dev_1cm 2022. 1. 19. 04:25
반응형

2022. 01. 07

 

MyBatis 정리

1, 2교시 중간때 까지는 이전에 했었던 Mybatis를 전체적으로 다시 훑어보았다.

 

 

log4j

로그란?

 - 소프트웨어에서 발생하는 이벤트를 기록하는 것

 - 파일로 대부분 관리하게 된다.

 

-> 왜 중요할까?

  -> 소프트웨어에서 문제 발생 시 문제 지점을 찾을 수 있고, 사용자의 행위 기록도 가능함(데이터 분석)

 

log4j framework

 - 분산 처리 환경에서 여러 서버에 있는 로그들을 수집하는 역할도 한다.

 - 가장 오래됐다.

 

logback

 - log4j의 단점들을 개선해서 만들어진 프레임워크

 

log4j2

 - 가장 최근에 나온 프레임워크

 - logback보다 좀 더 빠르고, logback에서의 문제점들을 개선했다.

 

로그 작성 시 정확하게 들어가야 하는 사항

 - 애플리케이션의 동작을 구체적으로 설명

 - 로그 수집 시 기존 성능을 저하시키지 않아야 함

 - 어떠한 환경에서든 유연하게 수집할 수 있어야 함

 -> 이러한 것들을 다 지원해주기 위해 프레임 워크를 사용해준다.

 

각 프로그래밍 언어마다 고유한 로그 프레임워크가 따로 있다.

 - 자바 : log4j, logback

-> 수업에서는 SLF4J와 log4j를 같이 사용할 것임

 

SLF4J란?

 -> Simple Logging Facade for Java의 약자로, 로그 프레임워크에 접근할 수 있는 API라고 생각하면 된다.

 -> 로그에 대한 파사드 패턴(Facade Pattern)이다.

 

SLF4J와 log4j를 활용하는 예시

 

 

mvnrepository에서 log4j 검색 후 바인딩된 API를 pom.xml에 추가해준다.

 

	<!-- logging 관련 라이브러리 -->
	<!-- https://mvnrepository.com/artifact/org.apache.logging.log4j/log4j-slf4j-impl -->
	<dependency>
	    <groupId>org.apache.logging.log4j</groupId>
	    <artifactId>log4j-slf4j-impl</artifactId>
	    <version>2.17.1</version>
	    <scope>test</scope>
	</dependency>

 

그리고 maven update 후 패키지에 log4j관련된 jar가 들어가 있는지 확인

 

log4j 버전 1.xx는 log4j 1이고, log4j 2.xx버전들은 log4j2라고 생각하면 된다.

 

log4j2.xml 파일을 resources 아래에 생성해준다.

 

그리고 log4j 2 configuration복사해서 log4j2.xml파일에 넣어줌 -> 다듬고 다듬어서 (지우고 지워서)

 

Log4j – Configuring Log4j 2

Configuration Inserting log requests into the application code requires a fair amount of planning and effort. Observation shows that approximately 4 percent of code is dedicated to logging. Consequently, even moderately sized applications will have thousan

logging.apache.org

 

기본적인 부분들 먼저 본다.

<?xml version="1.0" encoding="UTF-8"?>

<Configuration status="INFO">
  <Appenders>
  	<Console name="console" target="SYSTEM_OUT">
		<PatternLayout pattern="[%-5level] %d{yyyy-MM-dd HH:mm:ss.SSS} [%t] %c{3} %M - %msg - %n "/>
    </Console>
  </Appenders>
  <Loggers>
  	<Root level="DEBUG">
      <AppenderRef ref="console"/>
    </Root>
  </Loggers>
</Configuration>

 

 

 

<?xml version="1.0" encoding="UTF-8"?>

<!-- status : 로그 설정 파일을 읽어갈 때 발생하는 로그들을 찍어주는 로그들의 레벨 (INFO로 찍으면 안 보임)  -->
<Configuration status="INFO">
  <!-- 로그의 출력 위치를 지정한다.(콘솔, 파일, OutputStream, ...) -->
  <Appenders>
  	<Console name="console" target="SYSTEM_OUT">
  		<!-- 로그의 출력 포맷을 지정한다. -->
  		<!-- 
  			%-5level : 디버깅 레벨
  			%d : 날짜
  			%t : 스레드 이름
  			%c : 어떤 클래스에서 찍히는지 {단계 설정}
  			%M : method
  		 -->
		<!-- <PatternLayout pattern="[%level] %d{yyyy-MM-dd HH:mm:ss.SSS} [%t] %c{3} %M - %msg - %n "/> -->
		<PatternLayout pattern="[%-5level] %d{yyyy-MM-dd HH:mm:ss.SSS} [%t] %c{3} %M - %msg - %n "/>
    </Console>
    <File name="file" fileName="./logs/test.txt">
		<PatternLayout pattern="[%-5level] %d{yyyy-MM-dd HH:mm:ss.SSS} [%t] %c{3} %M - %msg - %n "/>
    </File>
  </Appenders>
  
  <!-- 로깅이 일어나는 부분을 그룹화하는 역할을 한다. -->
  <Loggers>
  <!-- 일반적인 로그 정책을 의미. -->
  <!-- 
  	FATAL > ERROR > WARN > INFO > DEBUG > TRACE > ALL 
  	 : 로그 레벨을 조정해서 사용하는데, ALL에서 FATAL로 갈수록 레벨이 커진다고 생각하면 되는데,
  	  예를 들어 DEBUG 레벨일 시, DEBUG 레벨 포함한 큰 로그들을(FATAL, ERROR, WARN, INFO) 다 찍어준다.
  -->
  	<Root level="DEBUG">
      <AppenderRef ref="console"/>
      <AppenderRef ref="file"/>
    </Root>
  </Loggers>
  <!-- RollingFile appender : 로그파일의 크기가 일정 이상이 되면 새 파일을 생성하여 추가시켜줌  -->
</Configuration>

실행시켜주면 logs/test.txt 파일로 로그 파일이 생성되는 것을 확인할 수 있다.

 

 

 

로그 실습

pom.xml에 있는 scope - test 부분을 지워준다.

 

App.java

package com.kh.mybatis;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

/**
 * Hello world!
 *
 */
public class App {
	// 로그테스트
	private static Logger log = LoggerFactory.getLogger(App.class);
	
    public static void main( String[] args ) {
    	log.info("로깅 테스트");
    	
        System.out.println( "Hello World!" );
    }
}

 

 

롬복내에 있는 @Slf4j를 활용하게 되면 더 쉽게 작성할 수 있다.

 

package com.kh.mybatis;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import lombok.extern.slf4j.Slf4j;

/**
 * Hello world!
 *
 */
@Slf4j
public class App {
	// 로그테스트
	// @Slf4j으로 인해서 아래의 선언문은 생략이 가능하다.
	// private static Logger log = LoggerFactory.getLogger(App.class);
	
    public static void main( String[] args ) {
    	log.info("로깅 테스트");
    	
        System.out.println( "Hello World!" );
    }
}

 

 

MemberService.java에 적용해보기

@Slf4j 어노테이션 추가

 

 

로그 정책 정의

    <!-- 추가로 필요한 로그 정책을 정의한다. (패키지의 범위를 설정) -->
    <Logger name="com.kh.mybatis.member" level="DEBUG">
      <AppenderRef ref="file"/>
    </Logger>
  </Loggers>

특정 패키지의 범위를 설정하여 따로 로그를 기록할 수 있다.

 

응용해서 BoardService.java에도 적용해본다.

 

BoardService와 MemberService에 입력해준 로그들은 log4j2.xml파일에서 따로 파일을 생성해서 관리해줄 수 있다.

 

 

전체 실습 코드

> log4j2.xml

<?xml version="1.0" encoding="UTF-8"?>

<!-- status : 로그 설정 파일을 읽어갈 때 발생하는 로그들을 찍어주는 로그들의 레벨 (INFO로 찍으면 안 보임)  -->
<Configuration status="INFO">
  <!-- 로그의 출력 위치를 지정한다.(콘솔, 파일, OutputStream, ...) -->
  <Appenders>
  	<Console name="console" target="SYSTEM_OUT">
  		<!-- 로그의 출력 포맷을 지정한다. -->
  		<!-- 
  			%-5level : 디버깅 레벨
  			%d : 날짜
  			%t : 스레드 이름
  			%c : 어떤 클래스에서 찍히는지 {단계 설정}
  			%M : method
  		 -->
		<!-- <PatternLayout pattern="[%level] %d{yyyy-MM-dd HH:mm:ss.SSS} [%t] %c{3} %M - %msg - %n "/> -->
		<PatternLayout pattern="[%-5level] %d{yyyy-MM-dd HH:mm:ss.SSS} [%t] %c{3} %M - %msg - %n "/>
    </Console>
    <File name="file" fileName="./logs/member_log.txt">
		<PatternLayout pattern="[%-5level] %d{yyyy-MM-dd HH:mm:ss.SSS} [%t] %c{3} %M - %msg - %n "/>
    </File>
    
    <File name="file2" fileName="./logs/board_log.txt">
		<PatternLayout pattern="[%-5level] %d{yyyy-MM-dd HH:mm:ss.SSS} [%t] %c{3} %M - %msg - %n "/>
    </File>
  </Appenders>
  
  <!-- 로깅이 일어나는 부분을 그룹화하는 역할을 한다. -->
  <Loggers>
  <!-- 일반적인 로그 정책을 의미. -->
  <!-- 
  	FATAL > ERROR > WARN > INFO > DEBUG > TRACE > ALL 
  	 : 로그 레벨을 조정해서 사용하는데, ALL에서 FATAL로 갈수록 레벨이 커진다고 생각하면 되는데,
  	  예를 들어 DEBUG 레벨일 시, DEBUG 레벨 포함한 큰 로그들을(FATAL, ERROR, WARN, INFO) 다 찍어준다.
  	  
  	  additivity : false일 경우 지정된 곳에만 찍고, 중복으로 로그를 찍지 않게 해주는 속성
  -->
  	<Root level="DEBUG" additivity="false">
      <AppenderRef ref="console" />
      <!-- 
      <AppenderRef ref="file"/>
       -->
    </Root>
    
    <!-- 추가로 필요한 로그 정책을 정의한다. (패키지의 범위를 설정) -->
    <Logger name="com.kh.mybatis.member" level="DEBUG" additivity="false">
      <AppenderRef ref="file"/>
    </Logger>
    
    <Logger name="com.kh.mybatis.board" level="DEBUG" additivity="false">
      <AppenderRef ref="file2"/>
    </Logger>
  </Loggers>
  <!-- RollingFile appender : 로그파일의 크기가 일정 이상이 되면 새 파일을 생성하여 추가시켜줌  -->
</Configuration>

 

 

> App.java

package com.kh.mybatis;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import lombok.extern.slf4j.Slf4j;

/**
 * Hello world!
 *
 */
@Slf4j
public class App {
	// 로그테스트
	// @Slf4j으로 인해서 아래의 선언문은 생략이 가능하다.
	// private static Logger log = LoggerFactory.getLogger(App.class);
	
    public static void main( String[] args ) {
    	log.info("로깅 테스트");
    	
        System.out.println( "Hello World!" );
    }
}

 

 

BoardService와 MemberService에는 어노테이션이랑 log.info만 추가해줬다.

반응형
Comments