MockHttpServletResponse:
Status = 200
Error message = null
Headers = []
Content type = null
Body =
Forwarded URL = null
Redirected URL = null
Cookies = []
http resonse에 Body가 비어있다.
그에 따라 테스트 코드.andExpect(jsonPath("$.title").exists())에서 에러가 발생했다.
java.lang.AssertionError: No value at JSON path "$.title"
at org.springframework.test.util.JsonPathExpectationsHelper.evaluateJsonPath(JsonPathExpectationsHelper.java:304)
...
Caused by: java.lang.IllegalArgumentException: json can not be null or empty
@Test
@DisplayName("Board 데이터 생성 테스트")
void createBoardTest() throws Exception {
given(boardService.saveBoard(new BoardDto("title", "content", "boardType", t, t)))
.willReturn(new BoardResponseDto(123L, "title", "content", "boardType", t, t));
BoardDto boardDto = BoardDto.builder()
.title("title")
.content("content")
.boardType("boardType")
.regDate(t)
.chgDate(t)
.build();
Gson gson = new GsonBuilder().registerTypeAdapter(LocalDateTime.class, new GsonLocalDateTimeAdapter())
.registerTypeAdapter(LocalDateTime.class, new GsonLocalDateTimeAdapter()).create();
String content = gson.toJson(boardDto);
mockMvc.perform(
post("/board")
.content(content)
.contentType(MediaType.APPLICATION_JSON))
.andExpect(status().isOk())
.andExpect(jsonPath("$.title").exists())
.andExpect(jsonPath("$.content").exists())
.andExpect(jsonPath("$.boardType").exists())
.andExpect(jsonPath("$.regDate").exists())
.andExpect(jsonPath("$.chgDate").exists())
.andDo(print());
verify(boardService).saveBoard(new BoardDto("title", "content", "boardType", t, chgT));
}
하지만 아래와 같이 포스트맨으로 테스트했을 땐 문제가 없다.

그럼 문제는 내 테스트 코드 내에 있다는 의미가 된다.
any()given(boardService.saveBoard(any()))
.willReturn(new BoardResponseDto(123L, "title", "content", "boardType", t, t));
given() 부분에 any()를 줘서, 어떤 값이 들어가던 willReturn()을 반환하게 한다.
그러나 코드를 이런 식을 수정할 경우, 요청값과 응답값이 같은지를 확인해주지 않는다. 따라서 exists() 부분을 수정해줘야한다.
mockMvc.perform(
post("/board")
.content(content)
.contentType(MediaType.APPLICATION_JSON))
.andExpect(status().isOk())
.andExpect(jsonPath("$.boardId").value(123L))
.andExpect(jsonPath("$.title").value("title"))
.andExpect(jsonPath("$.content").value("content"))
.andExpect(jsonPath("$.boardType").value("boardType"))
.andExpect(jsonPath("$.regDate").value("2023-09-02T17:30:00"))
.andExpect(jsonPath("$.chgDate").value("2023-09-02T17:30:00"))
.andDo(print());
존재여부만을 검증하는 것이 아닌 실제 값이 일치하는지를 검증하게 만든다.
verify(boardService).saveBoard(new BoardDto("title", "content", "boardType", t, chgT));
테스트 코드 맨 마지막 줄에 있던 verify() 부분을 아래와 같이 수정해준다.
verify(boardService).saveBoard(refEq(boardDto));
refEq() 메서드는 하나의 클래스에서 선택한 필드를 제외하고, given에서 주어진 값과 리플렉션이 동일한 객체인수를 확인하는 데 사용된다.
리플렉션이란, 컴파일 시점에서는 알 수 없는 클래스, 메서드의 이름을 런타임시점에서 메타정보를 이용해 획득하는 기술이다.
설명에 나와있는 동적 바인딩이란, 내가 작성한 코드의 클래스 타입을 자동으로 연결시켜주는다는 의미인 듯 하다.
어쨌든 해결하였다.