ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • 날짜 타입 JSON 변환에 관한 고찰
    스프링 2023. 5. 15. 16:53

    Spring을 사용할 경우 Controller에서 요청 받는/응답 주는 DTO에서 LocalDate와 LocalDateTime을 사용할 경우가 있다.

    헌데 이럴 경우 많은 사람들이 String으로 받은 후 서비스 레이어에서 변환해서 처리하도록 한다.

    이를 어노테이션으로 간단하게 처리하는 방법을 아라보자.

     

    Request Parameter를 통해 이를 알아보자.


    보통 Get 요청시 URL Parameter로 필드 데이터를 명시할때가 많다.
    Spring에선 이를 2가지 방법으로 해결할 수 있습니다.

    • @ModelAttribute로 DTO 객체를 받는다.
    • @RequestParamter로 필드별로 받는다.

    여기서 이 2가지에서 어떻게 LocalDate와 LocalDateTime을 직렬화 해서 받을 수 있는지 보도록 하자.

     

    아래와 같은 Controller 메소드가 있다고 가정.

    @GetMapping("/get")
    public String get(GetModel getModel) {
        log.info("get 요청 데이터 = {}", getModel);
    
        return "get 성공";
    }

    @ModelAttribute을 지정하지 않아도 별도로 어노테이션 지정이 없으면 @ModelAttribute을 자동 할당합니다.

    HTTP GET 요청을 /get 주소로 보내면 URL 파라미터의 각 필드들이 GetModel의 필드에 매핑되는 코드이다.

    그리고 GetModel의 코드는 아래와 같다.

    @ToString
    @Getter
    @Setter
    @NoArgsConstructor
    public class GetModel {
        private String name;
        private LocalDateTime requestDateTime;
    }

    테스트 대상인 LocalDateTime 아무런 어노테이션이 할당되어 있지 않다.

    아래와 같이 MVC테스트를 진행해보자.

    @RunWith(SpringRunner.class)
    @WebMvcTest
    public class ApplicationTest {
    
        @Autowired
        private MockMvc mockMvc;
    
        @Test
        public void ModelAttribute의_LocalDate는_변환된다() throws Exception {
            //given
            String url = "/get?name=jojoldu&requestDateTime=2018-12-15T10:00:00";
    
            //when
            ResultActions resultActions = this.mockMvc.perform(get(url));
    
            //then
            resultActions
                    .andExpect(status().isOk())
                    .andExpect(content().string(containsString("get 성공")));
    
        }
    }

    테스트가 실패한ㄷ다.
    이유는 requestDateTime을 직렬화 하지 못했다는 것이요.

    많은 분들이 이 부분에서 실패하고 String으로 그냥 받아서 처리한다.

    이를 해결하기 위해 먼저 @JsonFormat을 사용해보도록 하자.

     

    @ToString
    @Getter
    @Setter
    @NoArgsConstructor
    public class GetModel {
        private String name;
    
        @JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd'T'HH:mm:ss", timezone = "Asia/Seoul")
        private LocalDateTime requestDateTime;
    }

    이또한 실패하는 것을 볼 수 있다.

    여기서 해결할 수 있는 방법은 바로 @DateTimeFormat이다.
    @DateTimeFormat Spring에서 지원하는 어노테이션으로 LocalDate LocalDateTime와 같은 날짜 관련 타입의 직렬화를 지원하는 어노테이션이다.

    날짜 직렬화가 필요할 경우 @DateTimeFormat을 사용하면 된다는 것을 확인할 수 있다..

    728x90

    '스프링' 카테고리의 다른 글

    Mock에대한 고찰  (0) 2023.07.23
    MockMVC의 perform  (0) 2023.07.21
    노출하고싶지 않은 Json값  (1) 2023.04.13
    Junit Access denied for user  (0) 2023.04.05
    MultipartFile With Json  (0) 2023.04.03

    댓글

Designed by Tistory.