背景: 最近接到一个老项目需求,之前开发的WPS开放平台文件(商密集成)预览功能因为升级需要重新对接api,新的上传文件接口踩坑特意记录一下。
这里出问题的是第二步,请求文件上传信息
踩坑代码 调用后403 postman粘贴请求头和地址发起模拟调用成功
private String upload(StoreRequest storeRequest, File file) throws IOException, URISyntaxException {
URI url = new URIBuilder(storeRequest.getUrl()).build();
HttpHeaders headers = new HttpHeaders();
List<Header> storeRequestHeaders = storeRequest.getHeaders();
storeRequestHeaders.forEach(header -> headers.add(header.getName(), header.getValue()));
byte[] fileBytes = Files.readAllBytes(file.toPath());
HttpEntity<byte[]> requestEntity = new HttpEntity<>(fileBytes, headers);
return restTemplate.postForObject(url,requestEntity, String.class).getBody();
}
修改后:
private String upload(StoreRequest storeRequest, File file) throws IOException, NoSuchAlgorithmException, KeyStoreException, KeyManagementException {
// 1. 读取文件为字节数组
byte[] fileBytes = Files.readAllBytes(file.toPath());
// 2. 创建信任所有证书的 HttpClient
SSLContext sslContext = new SSLContextBuilder()
.loadTrustMaterial(null, (chain, authType) -> true)
.build();
try (CloseableHttpClient httpClient = HttpClients.custom()
.setSSLContext(sslContext)
.setSSLHostnameVerifier(NoopHostnameVerifier.INSTANCE)
.build()) {
// 3. 创建 POST 请求
HttpPost httpPost = new HttpPost(storeRequest.getUrl());
// 4. 设置 Headers(保持原始 Content-Type)
List<Header> storeRequestHeaders = storeRequest.getHeaders();
storeRequestHeaders.forEach(header ->
httpPost.addHeader(header.getName(), header.getValue())
);
// 5. 设置请求体(二进制数据)
ByteArrayEntity requestEntity = new ByteArrayEntity(fileBytes);
httpPost.setEntity(requestEntity);
// 6. 执行请求并获取响应
HttpResponse response = httpClient.execute(httpPost);
org.apache.http.Header[] headers = response.getHeaders("X-Wps3-Info-Token");
// 7. 返回响应头中的 Token
return headers[0].getValue();
}
}
问题原因
使用RestTemplate会自动根据上传二进制文件自动响应Content-Type为application/octet-stream
后与wps开发确认,此处的确是传空字符串。