복붙노트

[SPRING] resttemplate을 통한 spring rest 서비스를 통한 파일 전송

SPRING

resttemplate을 통한 spring rest 서비스를 통한 파일 전송

제목은 일반적으로 보일 수 있지만 내 문제에는 적합하지 않습니다.

나는 정상적인 매개 변수를 받아들이고 멀티 파트의 형태로 파일을 보내는 휴식 서비스를 가지고있다.

reststemplate을 사용하여 위의 rest service에 데이터와 파일을 보내고 싶습니다.

정상적인 문자열 데이터를 전송할 때까지 아무런 문제가 없었습니다. 일단 바이트를 보내는 코드를 추가하면 400 개의 잘못된 요청 오류가 발생하기 시작합니다.

ByteArrayResource를 전송하는 코드에 주석을 달면 일반 매개 변수로 작업하기 시작합니다.

아래는 샘플 코드입니다.

휴식 서비스 컨트롤러

@RestController
@RequestMapping(value="/ticket")
public class UserTicketController {

 @RequestMapping(value="/createTicket.do",method={RequestMethod.POST},
        consumes = {MediaType.MULTIPART_FORM_DATA_VALUE},headers={"content-type="+MediaType.MULTIPART_FORM_DATA_VALUE})
public void createTicket(@ModelAttribute ServiceDeskRequest serviceDeskRequest, HttpServletRequest request,HttpServletResponse response) throws Exception{

 }

 }

Servicedeskrequest 모델 속성

 public class ServiceDeskRequest implements Serializable{


private String jsonData;
private MultipartFile attachment;
}

application-context.xml

 <bean id="multipartResolver" class="org.springframework.web.multipart.commons.CommonsMultipartResolver">
</bean> 

클라이언트 측 코드

RestTemplate restTemplate = new RestTemplate();
        MultiValueMap<String, Object> requestParamerterMap = new LinkedMultiValueMap<String, Object>();

        requestParamerterMap.add("jsonData", jsonData);
        MultipartFile attachment = userRequest.getAttachment();

        if(attachment!=null && attachment.getOriginalFilename()!=null) {
            ByteArrayResource byteArrayResource = new ByteArrayResource(attachment.getBytes(), attachment.getOriginalFilename());
            requestParamerterMap.add("attachment", byteArrayResource);
        }

        HttpHeaders headers = new HttpHeaders();
        headers.setContentType(MediaType.MULTIPART_FORM_DATA);

        HttpEntity<MultiValueMap<String, Object>> requestEntity = new HttpEntity<MultiValueMap<String, Object>>(requestParamerterMap, headers);


        String response = restTemplate.postForObject(targetUrl, requestEntity, String.class);

해결법

  1. ==============================

    1.나는 그것을 알아. 이 퍼즐에는 두 개의 조각이 있습니다. 서비스 코드는 변경되지 않습니다.

    나는 그것을 알아. 이 퍼즐에는 두 개의 조각이 있습니다. 서비스 코드는 변경되지 않습니다.

    위의 변경 후 클라이언트 코드는

           FormHttpMessageConverter converter = new FormHttpMessageConverter();
    
            RestTemplate restTemplate = new RestTemplate();
            restTemplate.getMessageConverters().add(converter);
    
            MultiValueMap<String, Object> requestParamerterMap = new LinkedMultiValueMap<String, Object>();
    
            requestParamerterMap.add("jsonData", jsonData);
    
            MultipartFile attachment = userRequest.getAttachment();
    
            if(attachment!=null && attachment.getOriginalFilename()!=null) {
                //ByteArrayResource byteArrayResource = new ByteArrayResource(attachment.getBytes(), attachment.getOriginalFilename());
    
                MultipartByteArrayResource resource = new MultipartByteArrayResource(attachment.getBytes());
    
               //pass file name sepratly 
               resource.setFilename(attachment.getOriginalFilename());
    
                requestParamerterMap.add("attachment", resource);
            }
    
            HttpHeaders headers = new HttpHeaders();
            headers.setContentType(MediaType.MULTIPART_FORM_DATA);
    
            HttpEntity<MultiValueMap<String, Object>> requestEntity = new HttpEntity<MultiValueMap<String, Object>>(requestParamerterMap, headers);
    
            String response = restTemplate.postForObject(targetUrls.get("sdCreateTicketsUrl"), requestEntity, String.class);
    
  2. ==============================

    2.첫째, value = "/ createTicket.do"는 REST 규칙과 다릅니다. 같은 / 티켓에 간다. 티켓 생성은 URL을 통한 POST를 통해 수행되어야합니다 : ... / tickets /

    첫째, value = "/ createTicket.do"는 REST 규칙과 다릅니다. 같은 / 티켓에 간다. 티켓 생성은 URL을 통한 POST를 통해 수행되어야합니다 : ... / tickets /

  3. from https://stackoverflow.com/questions/45471648/sending-file-over-spring-rest-service-via-resttemplate by cc-by-sa and MIT license