기준은 하나다

로그의 목적은 일이 벌어진 뒤에 무슨 일이었는지 재구성하는 것이다. 이 기준으로 보면 판단이 단순해진다.

“이 줄이 없으면 장애 상황을 설명할 수 있는가?” 설명할 수 있으면 빼도 된다.

레벨을 기준으로 정한다

레벨을 감으로 붙이면 나중에 아무 의미가 없어진다. 기준을 정해둔다.

가장 흔한 실수는 잡아서 처리한 예외를 ERROR로 남기는 것이다. 정상 흐름으로 복구했다면 ERROR가 아니다. ERROR가 하루 수천 건 쌓이면 아무도 보지 않게 되고, 진짜 오류가 묻힌다.

구조화 로그와 상관관계 ID

문자열을 이어붙인 로그는 사람은 읽어도 검색이 어렵다. JSON으로 남기면 필드로 조회할 수 있다.

{"level":"ERROR","trace_id":"a1b2c3","user_id":1042,
 "event":"payment_failed","reason":"insufficient_balance","amount":15000}

특히 요청마다 고유 ID를 부여하고 모든 로그에 싣는 것이 중요하다. 서비스를 넘나드는 요청도 ID 하나로 전체 흐름을 이어 볼 수 있다. MDC나 트레이싱 컨텍스트로 자동 전파되게 해둔다.

남기면 안 되는 것

로그는 여러 곳에 복제되고 오래 보관되며 접근 권한이 느슨한 편이다. 한 번 찍히면 회수하기 어렵다.

식별이 필요하면 원본 대신 ID나 마스킹된 값을 남긴다. 직렬화 시 특정 필드를 자동으로 가리도록 설정해두는 편이 사람이 매번 조심하는 것보다 안전하다.

비용

로그는 공짜가 아니다. 수집·저장·검색 모두 비용이고, 디스크 I/O는 애플리케이션 성능에도 영향을 준다.

정리

“많이 남기기”가 아니라 “재구성할 수 있게 남기기”가 목표다. 레벨 기준을 팀에서 합의하고, 개인정보는 애초에 들어갈 수 없게 막아두는 것부터 시작한다.