[Wildfly] LOG 설정

오래된 로그를 어떻게 지울 것인가? wildfly의 standalone/log 폴더에는 아래와 같이 생성된다.

server.log
server.log.2020-03-01
server.log.2020-03-02
...
server.log.2020-03-10

이런 식으로 로그파일이 만들어지는 이유는 wildfly의 logging 서브시스템에 아래와 같이 periodic-rotating-file-handler가 설정되어 있어서 그렇다. 이것이 기본값이다.

<periodic-rotating-file-handler name="FILE" autoflush="true">
    <formatter>
        <named-formatter name="PATTERN"/>
    </formatter>
    <file relative-to="jboss.server.log.dir" path="server.log"/>
    <suffix value=".yyyy-MM-dd"/>
    <append value="true"/>
</periodic-rotating-file-handler>
또 다른 logging 시스템
<subsystem xmlns="urn:jboss:domain:logging:1.5">
    <size-rotating-file-handler name="FILE" autoflush="true" rotate-on-boot="true">
        ...
        <rotate-size value="400m"/>
        <max-backup-index value="20"/>
        <append value="false"/>
    </size-rotating-file-handler>
    ...
</subsystem>
<periodic-size-rotating-file-handler name="FILE" autoflush="true">
    <formatter>
        <named-formatter name="PATTERN"/>
    </formatter>
    <file relative-to="jboss.server.log.dir" path="server.log"/>
    <suffix value=".yyyy-MM-dd"/>
    <append value="true"/>
    <max-backup-index value="4"/>
    <rotate-size value="10000k"/>
    <encoding value="UTF-8"/>
</periodic-size-rotating-file-handler>

이 설정은 적용해보지는 못했는데, 오래된 wildfly라면 안될 수도 있다.(예전 문서에서 이 내용을 찾을 수가 없어서 이렇게 생각중임) 그 경우에는 커스텀하게 작성할 수도 있을 것 같다.

커스텀 로그 핸들러

체크 사항

위 설정 중 기본 값인 periodic-rotating-file-handler은 하루에 쌓이는 로그를 server.log 파일 한 개에 담아두고, 다음 날이 되면, suffix를 붙여서 보관해두는 방식이다. 하루에 한 개씩이라서 관리하기도 좋고 편해보이지만, 이 방식은 로그 파일이 지나치게 커지는 경우를 고려하지 않는 것이 단점이다. 로그 파일 하나가 2GB, 3GB, 300GB 이런식으로 커진다면 좋은 선택은 아니다. 300GB짜리 로그를 열어 볼 수 있는 에디터도 없을 듯..

하지만 로그의 양이 하루에 1GB를 넘지 않는 시스템이 많으므로, 대부분의 시스템에서는 이 방식이 문제 되지 않을 것이다.

로그 시스템에서 요구사항

이를 위해 가장 좋은 방법은 logrotate일 것 같다.

wildfly와 logrotate 주의사항

$ man logrotate

maxage count
    Remove rotated logs older than <count> days. The age is only checked if the logfile
    is to be rotated.
postrotate
    find /app/root/log/s0101 -name "*.gz" -mtime +30 -delete
endscript

/etc/logrotate.d/ 폴더에 wildfly 파일을 만들어서 아래의 내용을 작성한다.

/app/root/log/s0101/server.log.2*
{
	daily
	rotate 1
	missingok
	ifempty
	compress
	sharedscripts
	postrotate
		find /app/root/log/s0101 -name "*.gz" -mtime +30 -delete
	endscript
}

위의 로그 설정이 요구사항을 만족하는지 체크해보자. 로그 폴더에 아래의 파일이 있다고 했을 때

server.log
server.log.2020-03-01
server.log.2020-03-02
...
server.log.2020-03-10

logrotate를 실행하면

$  logrotate -f /etc/logrotate.d/wildfly

아래와 같이 압축된 형태로 파일이 생성된다.

server.log
server.log.2020-03-01.1.gz
server.log.2020-03-02.1.gz
...
server.log.2020-03-10.1.gz

이들 파일은 postrotatefind -mtime +30 명령에 의해 30일이 지나면 삭제될 것이다.

logrotate 대상의 문제점

위의 설정은 그럴 듯 해보이지만 제대로 동작하지 않는다. logrotate의 대상을 server.log.2*로 설정했기 때문에 server.log.2020-03-01.1.gz 파일도 대상이 된다. .gz 파일은 logrotate에서 제외시켜야 한다.

정규표현식을 사용할 수 있다. [!.][!g][!z]

/app/root/log/s0101/server.log.2*[!.][!g][!z]
{
        ... 나머지는 동일 ...
}

로그 파일은 logrotate에 의해 gz 파일로 압축되고, 위 설정은 확장자가 .gz인 파일은 logrotate 대상에서 제외하는 설정이다. stackoverflow logrotate 정규표현식 참고

olddir 옵션을 사용하는 것이 좋다.

gz파일을 제외시키기 위해 정규표현식을 사용할 수도 있지만, gz 파일을 아예 다른 폴더에 넣어 둘 수도 있다. 예를 들면 archived 폴더에 오래된 로그를 보관하는 것이 더 나을 것이다.

이를 위해 logrotate의 olddir 설정을 사용한다.

이 방식 보다는 압축된 파일을 특정 폴더에 옮겨주는 것이 더 나을 것 같다.

/app/root/log/s0101/server.log.2*[!.][!g][!z]
{
        ... 나머지는 동일 ...
        olddir archived
}

$  mkdir /app/root/log/s0101/archived

완성된 최종 버전의 logrotate 설정은 다음과 같다.

gz 파일을 제외하는 정규표현식과 olddir 설정을 모두 사용했다.

/app/root/log/s0101/server.log.2*[!.][!g][!z]
{
	daily
	rotate 1
	missingok
	ifempty
	compress
	olddir archived
	sharedscripts
	postrotate
		find /app/root/log/s0101/archived -name "*.gz" -mtime +30 -delete
	endscript
}

몇 줄 안되는 logrotate 설정을 이해하는데 고려해야 할 사항이 많은 것 같다.