공부공부/Spring Boot

[Spring] 컨트롤러 테스트하기

이숭간 2021. 5. 31. 18:36
728x90

스프링에서 컨트롤러 테스트하기

Controller테스트는 Service/Repository 테스트에 비해 상대적으로 테스트하기가 까다롭다. 

컨트롤러는 사용자의 HTTP Request를 처리하고 HTTP Response를 반환하는 객체이기 때문에 이를 테스트하기 위해서는 웹서버가 동작해야하고 요청과 반환을 담당하는 HttpServeletRequest/HttpServletResponse를 직접 구현해야한다.

 

하지만 이제는 스프링에서 지원하는 MockMvc를 이용하면 아주 간단하게 URL요청을 GET,POST,PUT, DELETE와 같은 REST형태로 요청을 테스트할수 있다.

 

MockMvc를 주입받는 2가지 방법

1. @SpringBootTest + @AutoConfigureMockMvc 애노테이션 붙이기

@RunWith(SpringRunner.class)
@SpringBootTest
@AutoConfigureMockMvc
public class MyControllerTest {
 @Autowired
 private MockMvc mockMvc;
 ...

 

2. @WebMvcTest 애노테이션 붙이기

@RunWith(SpringRunner.class)
@WebMvcTest
public class MyControllerTest {
 @Autowired
 private MockMvc mockMvc;
 ...

1번방법은 통합테스트를 할때,

2번방법은 MVC쪽만 슬라이스테스트할때 주로 사용한다.

2번처럼 @WebMvcTest 어노테이션을 이용하면 @Controller, @ControllerAdvice, @JsonComponent, Conver등의 어노테이션만 빈으로 등록해준다. 따라서 Serviece등이 테스트로직에 필요하다면 따로 MockBean을 이용해서 빈으로 등록한후에 주입받아 사용해야한다.https://devlog-wjdrbs96.tistory.com/189

MockMvc 사용하기

 @Test
    public void home이_리턴됨() throws Exception {
        String home = "home";

        // perform() - 요청을 전송하는 역할, 결과로 ResultActions객체를 받고, 이 객체에서 리턴값을 검증하고 확인할 수 있는 andExcpect()메소드를 제공함.
        mvc.perform(get("/"))
                //상태코드 -> isOk()는 상태코드 200
                .andExpect(status().isOk())
                // 응답본문의 내용을 검증함 -> Controller에서 'home'을 리턴하기 때문에 이값이 맞는지 검증한다.
                .andExpect(content().string(home));
    }
    @Test
    public void helloDto가_리턴됨() throws Exception {
        String name = "hello";
        int amount = 1000;

        mvc.perform(
                get("/dto")
                        // param -> api테스트할때 사용될 요청 파라미터를 설정한다. (단 값은 string만 허용되므로 숫자나 날짜는 문자열로 변공후 사용)
                        .param("name", name)
                        .param("amount", String.valueOf(amount)))
                .andExpect(status().isOk())
                //jsonPath -> JSON응답값을 필드별로 검증할 수 있는 메소드
                // $를 기준으로 필드명을 명시한다.
                .andExpect(jsonPath("$.name", is(name)))
                .andExpect(jsonPath("$.amount", is(amount)));
    }

 

 

 

참고링크
https://m.blog.naver.com/PostView.naver?isHttpsRedirect=true&blogId=genycho&logNo=221014013673

https://devlog-wjdrbs96.tistory.com/189