Spring RestTemplate POST文件,带有UTF-8文件名

时间:2017-10-23 09:17:33

标签: rest encoding utf-8 special-characters resttemplate

我正在使用Spring RestTemplate执行发送PDF文件的POST请求。文件名包含一些UTF-8字符(例如é,è,à,ê,ë)。

问题是,在发送请求后,在收到请求的另一端,文件名没有预期的UTF-8字符,我有类似的东西?popi?.pdf。

我试图在RestTemplate中明确设置UTF-8字符集,但它仍然不起作用。

这是我的代码,

public SomeThing storeFile(InputStream content, String fileName) {
    Charset utf8 = Charset.forName("UTF-8");
    RestTemplate restTemplate = new RestTemplate();

    HttpHeaders headersFile = new HttpHeaders();
    headersFile.setContentType(MediaType.APPLICATION_OCTET_STREAM);
    headersFile.setContentDispositionFormData("file", fileName);
    List<Charset> listCharSet = new ArrayList<Charset>();
    listCharSet.add(utf8);

    headersFile.setAcceptCharset(listCharSet);

    InputStreamResource inputStreamResource = new InputStreamResource(content);
    HttpEntity<InputStreamResource> requestEntityFile = new HttpEntity<>(inputStreamResource, headersFile);

    MultiValueMap<String, Object> multipartRequest = new LinkedMultiValueMap<>();
    multipartRequest.add("file", requestEntityFile);

    RestTemplate newRestTemplate = new RestTemplate();

    MappingJackson2HttpMessageConverter mappingJackson2HttpMessageConverter = new MappingJackson2HttpMessageConverter();
    HttpMessageConverter stringHttpMessageConverter = new StringHttpMessageConverter(Charset.forName("UTF-8"));
    newRestTemplate.getMessageConverters().add(0, stringHttpMessageConverter);
    newRestTemplate.getMessageConverters().add(mappingJackson2HttpMessageConverter);
    FormHttpMessageConverter convForm = new FormHttpMessageConverter();
    convForm.setCharset(utf8);
    newRestTemplate.getMessageConverters().add(convForm);

    HttpHeaders header = new HttpHeaders();
    header.setContentType(MediaType.MULTIPART_FORM_DATA);
    HttpEntity<MultiValueMap<String, Object>> requestEntity = new HttpEntity<>(multipartRequest, header);
    ResponseEntity<String> result = newRestTemplate.postForEntity(env.getProperty("core.endpoint") + "/documents", requestEntity, String.class);

}

2 个答案:

答案 0 :(得分:2)

根据rfc7578,当您发布包含多部分/表单数据的文件时,应使用“百分比编码”而不是文件名*

  

注意:[RFC5987]中描述的编码方法将添加一个   不得使用Content-Disposition标头字段中的“ filename *”参数。

很容易实现:

        RestTemplate restTemplate = new RestTemplate();
        restTemplate.getMessageConverters().add(0, new FormHttpMessageConverter() {
            @Override
            protected String getFilename(Object part) {
                if (part instanceof Resource) {
                    Resource resource = (Resource) part;
                    try {
                        return URLEncoder.encode(resource.getFilename(), "UTF-8");
                    } catch (UnsupportedEncodingException e) {
                        e.printStackTrace();
                        return null;
                    }
                } else {
                    return null;
                }
            }
        });

答案 1 :(得分:0)

很可能没有明确设置所使用的JVM的文件编码系统属性,同时运行JVM的操作系统不使用UTF-8作为默认字符集。例如,如果JVM在Windows上运行,并且我们没有指定charset,则默认值将是Windows-1252。

你能仔细检查发送和接收文件的两个应用程序的JVM参数吗?在指定主类名之前,请确保它具有 -Dfile.encoding = UTF-8 参数。

请确保接收文件的应用程序/服务已配置为接受UTF-8字符集。

如果在JVM上添加file.encoding参数并没有帮助解决问题,请随意检查其他可能相关的答案,