我使用AWS S3客户端从S3下载大文件(大约600MB)。但在下载过程中,下载失败,出现Socket closed
或Premature end of Content-Length delimited message body
或Data received in non-data state: 6
等错误。错误信息从一个失败到另一个失败不断变化。在一点点研究中,当AmazonS3
客户端在输入流完全读写之前被垃圾收集时,似乎会出现这样的问题。https://forums.aws.amazon.com/thread.jspa?messageID=438171
下面是代码的样子
public void retrieve(String bucket, String key, String localFile){
AmazonS3 s3Client = createNewS3Client();
S3Object object = s3Client.getObject(bucket, key);
InputStream inputStream = object.getObjectContent();
OutputStream outputStream = new FileOutputStream(localFile);
//read bytes from inputstream and write to outputstream until EOF
writeBytes(inputStream, outputStream);
inputStream.close();
outputStream.close();
}
所以我的问题是-如果方法writeBytes
需要更长的时间才能完成并返回,那么上述方法中的s3Client
可以被垃圾收集吗?writeBytes
方法中没有对s3Client
的引用
不可以。
在这里加上我的答案,实际上解决了问题。
不工作的地方:为了避免垃圾收集,我在末尾添加了一条使用s3Client
对象的日志语句。
正如人们在评论中建议的那样,使s3Client
成为课堂上的一个字段是一种选择,但我无法做出这种改变。这可能已经解决了这个问题。
修复问题:使用API getObject(GetObjectRequest GetObjectRequest, filedestinationfile)。它负责流处理,从流中读取内容并写入文件。