게시물에 이미지를 첨부하는 기능을 구현하면서 @RequestBody
로 DTO를, @RequestParam
으로MultipartFile을 함께 입력받고자 했다. Content-Type이 다른 두 가지 데이터를 한 번에 입력 받은 적이 없어서 기존처럼 구현했더니 에러가 발생했다.
@PostMapping(consumes = MediaType.MULTIPART_FORM_DATA_VALUE, produces = MediaType.APPLICATION_JSON_VALUE)
public ResponseEntity<Void> writePost(
@RequestBody WritePostRequest request,
@RequestParam("image") MultipartFile image) throws IOException {
postService.writePost(request, image);
return ResponseEntity.noContent().build();
}
Swagger로 테스트하니 다음과 같은 415(지원되지 않는 미디어 유형)오류가 생겼다.
"Content-Type 'multipart/form-data;boundary=----WebKitFormBoundarykAE7PKpAiKkbsfIt;charset=UTF-8' is not supported.",
알아보니 multipart/form-data와 JSON(or XML)을 함께 입력 받기 위해선 @RequestPart
어노테이션을 사용해야 한다.
@PostMapping(consumes = MediaType.MULTIPART_FORM_DATA_VALUE, produces = MediaType.APPLICATION_JSON_VALUE)
public ResponseEntity<Void> writePost(
@RequestPart(value = "request") WritePostRequest request,
@RequestPart(value = "image") MultipartFile image) throws IOException {
postService.writePost(request, image);
return ResponseEntity.noContent().build();
}
Swagger로 데이터를 전달하니 다음과 같은 오류가 발생한다.
"detail": "Content-Type 'application/octet-stream' is not supported.",
Postman으로 테스트를 진행해도 되지만, react 개발을 하는 팀원과 Swagger을 통해 소통하는 중이므로 Swagger로 테스트가 가능하길 바랐다.
그래서 여기를 참고하여 수정했다.
@PostMapping(consumes = MediaType.MULTIPART_FORM_DATA_VALUE, produces = MediaType.APPLICATION_JSON_VALUE)
public ResponseEntity<Void> writePost(
@RequestPart(value = "request") @Parameter(schema =@Schema(type = "string", format = "binary")) WritePostRequest request,
@RequestPart(value = "image") MultipartFile image) throws IOException {
postService.writePost(request, image);
return ResponseEntity.noContent().build();
}
request엔 JSON 파일을, image엔 이미지 파일을 첨부하면 정상적으로 실행된다.
Converter
또는 PropertyEditor
를 통한 형식 변환에 의존한다.Content-Type
헤더를 고려하는 HttpMessageConverters
에 의존한다.