Deserialization Failure due to Date Format
Deserialization Failure due to Date Format(날짜 포맷 역직렬화 실패)
지금 개발하고 있는 부분에 날짜 포맷을 사용해야 하는 부분이 있었다.
사용자가 해당 날짜를 수정해서 저장도 가능하고, 저장한 값들은 불러올 수도 있어야 한다.
하지만 시간 저장이 안되는 문제가 발생했다!!
오늘의 오류 공부하기
⚠️문제
필드에서 날짜를 입력후 저장하게 되면 500에러 발생
❔원인
프론트에서 날짜에 대한 type 값이 여러개 있는데
type="text"는 날짜, 시간 선택에 대한 범위가 없고 광범위하게 사용 가능하지만 기본 제공되는 달력 라이브러리나 이런 편의성이 없기 때문에 사용자가 직접 입력한것을 받아서 쓴다.
type=”date”는 날짜만 선택 가능하다. 지금 나의 경우에는 시간도 선택할 수 있어야 했기 때문에 사용할 수 없었다.
ex)YYYY-MM-DD
type=”datetime-local”은 날짜와 시간까지 선택할 수 있기 때문에 이걸로 사용을 했다.
<td><input type="datetime-local" name="startDateTime" v-model="form.clrmBeginDt" @click="showPicker($event)"></td>
<td><input type="datetime-local" name="endDateTime" v-model="form.clrmEndDt" @click="showPicker($event)"></td>
프론트에서 사용자한테 이렇게 입력을 받고 v-form action을 통해 api를 호출했다.
이렇게 되면 input이 datetime-local이니까 2025-04-10T19:30처럼 자동으로 T가 포함된 문자열을 생성하지만
(T는 날짜와 시간을 연결하는 ISO 8601 표준 포맷의 구분자라고 한다)
나는 백엔드에서 공백 구분자가 포함된 문자열만 역직렬화 가능하게 설정해놨었다.
@JsonFormat(pattern = "yyyy-MM-dd HH:mm")
private LocalDateTime clrmBeginDt;
이렇게 되니까 프론트에서는 이렇게 JSON을 보내는데
{
"clrmBeginDt": "2025-04-10T19:30"
}
백엔드에서는 T를 예상하지 않고 "" 공백을 예상했기 때문에 JackSon이 문자열을 LocalDateTime으로 변환하지 못하고 500에러를 내는것이였다.
✅해결
DTO에 @JsonFormat을 수정해서 해결했다.
@JsonFormat(pattern = "yyyy-MM-dd'T'HH:mm")
private LocalDateTime clrmBeginDt;
이렇게 하니까 "2025-04-10T19:30"으로 올바르게 파싱하고 프론트에서 전송한 값을 정상적으로 객체에 매핑해서 DB로 저장할 수 있었다.
+ 백엔드에서 프론트로 보낼때 T 지우기
백엔드에서 받아온 날짜 데이터는 이런 형태다.
"clrmBeginDt": "2025-04-10T19:30"
이 값을 그대로 프론트에서 출력하니까 2025-04-10T19:30이런식으로 이상한 T가 보였다.
그래서 반대로 T를 ""으로 바꿔서 표현하고 slice를 통해 초까지 확실히 제거해서 출력되게 했다.
form.value.clrmBeginDt = res.data.clrmBeginDt?.slice(0, 16).replace("T", " ");
form.value.clrmEndDt = res.data.clrmEndDt?.slice(0, 16).replace("T", " ");