Spring/Test

[Spring Test] 파일 업로드 컨트롤러 테스트 (File + Text)

ajeong7038 2024. 3. 3. 20:36

 

✨ 기존

- 기존 컨트롤러 테스트에서는 get or post 방식의 request를 생성하기 위해 MockMvcResultBuilders의 get(), post() 메서드를 이용하였다.

 

String body = objectMapper.writeValueAsString(dto);

        ResultActions perform = mockMvc.perform(post("/boards")
                .contentType(MediaType.APPLICATION_JSON)
                        .locale(Locale.KOREA)
                .content(body));

        // ControllerTest
        perform.andDo(print())
                .andExpect(status().isBadRequest())
                .andExpect(content().contentType(MediaType.APPLICATION_JSON))
                .andExpect(jsonPath("$.success").value(false))
                .andExpect(jsonPath("$.response.errorCode").value("BAD_INPUT"))
                .andExpect(jsonPath("$.response.errorMessage").value("입력이 올바르지 않습니다."))
                .andExpect(jsonPath("$.response.errors.title").value("공백일 수 없습니다"))
                .andExpect(jsonPath("$.response.errors.content").value("공백일 수 없습니다"));

 

requestBuilder을 이용해 perform 안의 값을 구성

// 1
ResultActions perform = mockMvc.perform(post("/boards")
                .contentType(MediaType.APPLICATION_JSON)
                        .locale(Locale.KOREA)
                .content(body));

// 2. 이걸 꺼내면
MockHttpServletRequestBuilder content = post("/boards")
                .contentType(MediaType.APPLICATION_JSON)
                        .locale(Locale.KOREA)
                .content(body);
ResultActions perform = mockMvc.perform(content);

// => 1과 2는 같은 코드. 1의 perform 안의 값을 변수로 꺼낸 것이 2이다

 

반면, row -> json 타입이 아닌 사진을 업로드하는 경우 multipart()를 사용해야 한다

- Multipart()의 반환 타입은 MockMultipartHttpServletRequestBuilder

- MockMultipartFile 클래스와 MockMultipartHttpServletRequestBuilder을 이용해 파일 등록 테스트 코드를 짠다

 

즉, 사진이 없는 JSON 형태 (row) 로 넣고 싶을 때는 MockHttpServletRequestBuilder을 사용하고, 파일을 등록 해야 하는 경우에는 MockMultipartHttpServletRequestBuilder을 사용한다

 

✨ File + Text를 동시에 넣어야 하는 경우

- 사진만 넣으면 되는 경우는 mockMvc.perform(builder).file(image)만 하면 되지만, Text를 form-data 안에 집어 넣어야 하는 경우

- File : .file()

- Text : .param("key", "value")

 

ex)

MockMultipartHttpServletRequestBuilder builder = multipart("/boards");

        builder.with(request -> {
            request.setMethod("POST");
            return request;
        });

        ResultActions perform = mockMvc.perform(builder
                .file(image)
                .param("title", "제목")
                .param("content", "내용")
                .contentType(MediaType.APPLICATION_JSON));

✨ 참고 자료

https://goodteacher.tistory.com/507