[Trouble Shooting] Spring HeapDump 설정 및 분석
신규 구축 프로젝트 중 erp application 서비스가 자꾸 죽는다고, ..
환경은 쿠버네티스 기반인데 OOM 떨어지게 개발해놓고 '나'한테 전화가 쏟아진다.
인프라 명목을 단정짓기위해 분석을 시작하고 팩트로 조져보자!
dump 경로 및 gc로그 설정
먼저 heapdump 옵션과 gc log 설정을 하여 모니터링 하기 위해 deployment yaml 에 설정을 추가해주었다.
spec:
template:
containers:
- args:
- -XX:+HeapDumpOnOutOfMemoryError
- -XX:HeapDumpPath=/덤프파일경로/
- -XX:+PrintGCDetails
- -verbose:gc
- -Xloggc:/가비지컬렉터로그경로/gc.log:time,level,tags
- -jar
- -Dspring.profiles.active=prod
- 실행될애플리케이션.jar
- -javaagent:dd-java-agent.jar
command:
- java
gc.log 모니터링
개발사에게 대용량 쿼리요청시 잘 처리해달라고 그렇게 말했으나... 역시나.... 여러 페이지에서 옵션으로 [전체조회] 버튼이 있었는데 29만 row의 데이터를 조회하는 페이지에서 눌러보니 memory가 미친듯이 올라가며 full gc가 수행되는걸 볼 수 있었다.
HeapDump 분석
heap dump가 떨어져 바로 파일을 옮겨 분석을 해보았다.(파일 사이즈는 약 4.2GB)
분석 프로그램은 Eclipse MemoryAnalyzer 를 이용하였다.
tomcat threads 1.6 G / mysql Result Set 1.5 GB 영역을 사용했다.
각 영역의 설명을 보니 결국 select에서 문제인 것 같다.
Hint 1 은 1번 문제가 2번과 관련이 있을 수 있다는 내용이다.
그럼 이제 더 상세하게 봐보자.
최상위 Object에서 List Objects > with outgoing을 눌러보니 아래와 같은 정보가 나온다
rowData들을 몇개 찍어보면 테이블명과 컬럼명들도 확인할 수 있다.
마무리
1.5기가의 heap을 사용하게 된 경위를 이렇게 찾을 수 있었다.
개발사가 테스트할 때부터 눈에 보이던 부분인데, 개발자들은 이걸 잘 안보는 거 같다..
mybatis를 사용할 때 어떻게 개선할 수 있는지 개인적으로 프로젝트를 해봐야겠다.