Spring boot 로그를 cloudwatch에 남겨보자!

Jinseok Lee·2022년 7월 14일
0
post-thumbnail

사연

서비스 오픈을 앞두고 어플리케이션의 로그들을 조금 더 쉽게 확인할 수 있는 방안이 필요했다. 현재는 베스천 서버를 만들고 서버를 들어가서 log파일을 직접 열어보는 방식이었다. 그래서 우리 서비스의 경우 현재 aws ec2에서 돌아가고 있었기에 cloudwatch를 활용하여 로그를 쌓으면 좋을거 같다는 결론을 내렸다.

사전 준비사항

iam 계정

aws cloudwatch에 로그를 적재하기위해서는 cloudwatch의 권한을 포함하는 aws iam 계정을 먼저 생성해주어야한다. 내 경우 iam 계정을 생성하고 CloudWatchLogsFullAccess 권한을 포함해서 계정을 생성했다.

aws credentials 설정

어플리케이션이 실행되는 인스턴스(ec2)에 aws credentials 정보가 등록되어 있어야 한다. iam 계정을 생성할때 받은 accessKeysecretKey 정보를 ~/.aws/credentials 파일에 설정해주어야 한다.
/home/ubuntu/.aws/credentials

[default]
# your aws iam
aws_access_key_id = your-access-key
aws_secret_access_key = your-secret-key

로그백 설정

gradle 의존성

dependencies {
    ...
    implementation group: 'ca.pjer', name: 'logback-awslogs-appender', version: '1.6.0'
    implementation 'org.codehaus.janino:janino:3.1.7'
	...
}

logback.xml

<?xml version="1.0" encoding="UTF-8"?>
<configuration>
  <appender name="ASYNC_AWS_LOGS" class="ca.pjer.logback.AwsLogsAppender">
    <filter class="ch.qos.logback.classic.filter.ThresholdFilter">
      <level>ERROR</level>
    </filter>
    <layout>
      <pattern>%d{yyyyMMdd'T'HHmmss} %thread %level %logger{15} %msg%n</pattern>
    </layout>
    <if condition='property("spring.profiles.active").contains("local")'>
      <then>
        <logGroupName>KPOP-API-local</logGroupName>
      </then>
    </if>
    <if condition='property("spring.profiles.active").contains("dev")'>
      <then>
        <logGroupName>KPOP-API-dev</logGroupName>
      </then>
    </if>
    <if condition='property("spring.profiles.active").contains("prod")'>
      <then>
        <logGroupName>KPOP-API-prod</logGroupName>
      </then>
    </if>
    <logStreamUuidPrefix>error-</logStreamUuidPrefix>
    <logRegion>ap-northeast-2</logRegion>
    <maxBatchLogEvents>50</maxBatchLogEvents>
    <maxFlushTimeMillis>30000</maxFlushTimeMillis>
    <maxBlockTimeMillis>5000</maxBlockTimeMillis>
    <retentionTimeDays>0</retentionTimeDays>
  </appender>
  
  <springProfile name="dev">
    <logger name="org.springframework" level="INFO" />
    <logger name="inc.bfactory.kpop" level="INFO"/>
    <root level="INFO">
      <appender-ref ref="ASYNC_AWS_LOGS" />
    </root>
  </springProfile>

</configuration>

janino라는 라이브러리는 까다롭게도 xml에서 if구문중 property를 다루기 위해서 필요했다. 현재 profiles 정보를 참고해서 로그그룹을 별도로 지정하기 위해서 필요했다.

테스트

@RestController
@Slf4j
public class HelloController {

    @GetMapping("/hello")
    public String hello() {
        log.error("aws log test");
        return "hello";
    }

}

테스트를 해보았더니 정상적으로 로그를 수집하는 것을 확인할 수 있었다.

추신

  • logback.xml의 경우 다른 설정들이 많기 때문에 주제와 멀어질 수 있어서 aws appender만 포함해서 작성했다. 전체 코드는 아니다.
  • 혹시 필자가 놓친 부분이 있어서 로그 수집이 안되거나 해서 화가 날수 있다. 댓글이나 이메일을 보내달라. (sonaky47@gmail.com)!
profile
전 위메프, 이직준비중

2개의 댓글

comment-user-thumbnail
2022년 7월 14일

xml의 ​​if 문의 속성을 처리하려면 janino라는 라이브러리가 필요하다는 것을 알고 있습니다. 현재 프로필 정보를 참조하여 로그 그룹을 구체적으로 지정해야 합니까?

1개의 답글