현재 진행 중인 프로젝트의 로그인 기능은 토큰을 사용한다.
해당 토큰은 만료일이 존재하기 때문에 시간 관리가 굉장히 중요한데,
시간이 맞지 않으면, 토큰이 항상 만료 상태일 위험이 있기 때문이다.

처음에 RDS와 EC2 Server는 시간이 UTC로 되어 있어서,
Amazon에서 직접 Parameter group을 설정해서 시간을 맞추고
터미널에서도 EC2에 SSH Protocol로 접속을 해서 서버 시간을 맞추었다.
기본 시간이 UTC이기 때문에 모두 Asia/Seoul 로 맞추었는데,
문제는 Postman의 응답에서 출력되는 만료 시간이었다.

분명 DB에서 select now()도 해보고 서버 시간을 확인해봐도,
모두 Asia/Seoul로 현재 우리나라의 시간과 동일하게 출력 됐다.
서버시간
KakaoTalk_20230222_165145310

하지만, 아래 생성된 토큰의 만료 일자를 확인해보면 9시간 차이가 남을 알 수 있다.
UTC 세계 표준시는 우리나라 보다 9시간 빠른 시간이므로, UTC` 임을 알 수 있다.
KakaoTalk_20230222_170440908

RDS와 EC2는 모두 설정을 해놓았으니, 의심해볼 것은 Spring Project 뿐이다.
조금 찾아보니, @PostConstruct를 통해 Timezone을 설정하는 방법이 있다고 한다.
해당 방법을 적용해 아래와 같이 코드를 작성했다.
KakaoTalk_20230222_165553378

하지만 결과는 실패. 아직 시간이 제대로 바뀌지 않았다.
아래와 같이 로그를 찍어보니, Spring Project도 Asia/Seoul 시간인 듯 하다.
그럼 도대체 뭐가 문제라서 결과 시간은 ```UTC``로 뜨는 것일까?
KakaoTalk_20230222_173748236
KakaoTalk_20230222_173759284

그래서 Postman의 Response Header를 한번 살펴보았다.
Response Header에 Date 항목이 현재 GMT(UTC)임을 볼 수 있다.
KakaoTalk_20230222_174715489

해당 응답은 서버에서 날아오는 것일텐데, 그럼 서버 시간이 문제일까?
위에서 확인한 서버 시간은 분명히 KST 한국 시간으로 설정되어 있었다.
기능 동작도 다 제대로 되는데, 왜 Postman 응답만 이런 것일까?

HTTP의 공식 문서인 RFC9110 과 Mozilla에서 제공하는 MDN 을 보니,
Date Header는 기본적으로 GMT(UTC)를 사용한다고 한다.
이 정보와는 딱히 연관이 없을 것 같다.
rfc
mdn

분명 나는 Date 객체를 담아서 JSON Response로 출력해주는 기능을 만들었는데,
Postman에는 왜 내가 담은 대로 출력이 안되고 UTC로 출력할까?

조금 더 찾아보니, JSON으로 변환하는 과정에서 아무래도 문제가 있는 것 같았다.
응답 시, JacksonObjectMapper가 동작해서 DTO를 Json으로 직렬화 하는데,
이 때 _serializationConfig의 기본 설정이 UTC 라고 한다.
이는 Jackson 라이브러리의 기본 값이며, 2.7 version 부터 그래왔다고 한다.

@JsonFormat Annotation을 사용하는 경우 Timezone을 지정할 수 있다고 한다.
이 방식을 이용하니 아래와 같이 제대로 출력된다!
KakaoTalk_20230222_230611197

제대로 동작을 하게 되었으니 다행이다.
찾은 정보가 쓸모는 없었지만 공식문서를 찾아보는 경험치는 +1 된 것 같은 기분이다.

참고문헌

MDN HTTP : Date
RFC 9110 HTTP : Date/Time Formats
Shane’s planet