我有2个服务A和B,用户可以向A请求下载文件。为此,服务A呼叫B询问该文件,获取该文件并以下载形式向用户发送响应。
我尝试这样做的方式是,服务B在控制器中获得正确的呼叫。然后,它从AWS获取File
对象,并从中创建FileSystemResource
,返回ResponseEntity<FileSystemResource>
。
我的问题是,当A收到响应时,它的主体为空。下载仍然发生,但我得到一个空文件(零字节)。知道我做错了什么吗?这可能吗?
我的服务A上的控制器
@GetMapping(value = "/get")
public ResponseEntity<FileSystemResource> downloadDocument(
HttpServletRequest httpServletRequest,
HttpServletResponse httpServletResponse
) {
httpServletResponse.setHeader(
"Content-Disposition",
"attachment; filename=" + filename);
httpServletResponse.setHeader(
"Content-Type",
"application/octet-stream"
);
return ResponseEntity.ok(
documentsService.getDocumentToDownload(fileName));
}
我的服务B上的控制器
@GetMapping(value = "/get")
public ResponseEntity<FileSystemResource> downloadDocument(
@RequestParam(value = "fileName") String fileName,
HttpServletResponse httpServletResponse
) {
File doc = documentsService.getFileForDocumentInS3(
fileName);
return ResponseEntity.ok(
new FileSystemResource(doc.getAbsolutePath())
);
}
这是我与AWS交互的服务(在服务B上)。请注意,我的aws3Client
变量是包含传输管理器的包装器。与AWS的连接性很好。
public File getFileForDocumentInS3(
String bucketName,
String fileKey
) {
try {
File toReturn = File.createTempFile(fileKey, ".tmp");
toReturn.deleteOnExit();
GetObjectRequest getObjectRequest = new GetObjectRequest(bucketName, fileKey);
awsS3Client.getTransferManager().download(getObjectRequest, toReturn);
return toReturn;
} catch (Exception ex) {
//catching exception here
}
}
答案 0 :(得分:1)
您在评论中提到您选择在服务之间发送文件,因为您无法为版本化存储桶中的特定版本生成签名URL。
自SDK版本1.11.123(当前最新版本为1.11.186)起,您可以使用GeneratedPresignedUrlRequest.withVersionId
设置签名网址的版本ID,如下所示:
final URL url = s3.generatePresignedUrl(
new GeneratePresignedUrlRequest("my-bucket", "my-key", HttpMethod.GET)
.withVersionId("version-id")
);