如何将S3对象写入文件?

时间:2011-10-06 20:13:07

标签: java amazon-web-services file-io amazon-s3

将S3对象(我有密钥)写入文件的最快方法是什么?我正在使用Java。

6 个答案:

答案 0 :(得分:25)

Java 7 (2011年7月发布)以来,有一种更好的方法:来自Files.copy()java.util.nio.file实用程序。

  

将输入流中的所有字节复制到文件中。

所以你需要既不 an external library也不需要推出自己的byte array loops。以下两个示例,两个示例都使用来自S3Object.getObjectContent()的输入流。

InputStream in = s3Client.getObject("bucketName", "key").getObjectContent();

1)在指定路径写入新文件:

Files.copy(in, Paths.get("/my/path/file.jpg"));

2)写入系统默认tmp位置的临时文件:

File tmp = File.createTempFile("s3test", "");
Files.copy(in, tmp.toPath(), StandardCopyOption.REPLACE_EXISTING);

(如果没有指定替换现有文件的选项,您将获得FileAlreadyExistsException。)

另请注意,getObjectContent() Javadocs强烈要求关闭输入流

  

如果检索S3Object,则应将此输入流关闭为   尽快,因为对象内容没有缓冲   内存和流直接来自Amazon S3。此外,未能关闭   此流可能导致请求池被阻止。

因此,最好将所有内容包装在try-catch-finally中,并在finally块中执行in.close();

以上假设您使用亚马逊的官方SDK(aws-java-sdk-s3)。

答案 1 :(得分:15)

虽然IOUtils.copy()IOUtils.copyLarge()很棒,但我更喜欢旧学校循环输入流,直到输入流返回-1。为什么?我之前使用过IOUtils.copy(),但是有一个特定的用例,如果我开始从S3下载一个大文件,然后由于某种原因,如果该线程被中断,下载将不会停止,它将一直持续到整个文件已下载。

当然,这与S3无关,只与IOUtils库有关。

所以,我更喜欢这个:

InputStream in = s3Object.getObjectContent();
byte[] buf = new byte[1024];
OutputStream out = new FileOutputStream(file);
while( (count = in.read(buf)) != -1)
{
   if( Thread.interrupted() )
   {
       throw new InterruptedException();
   }
   out.write(buf, 0, count);
}
out.close();
in.close();

注意:这也意味着您不需要额外的库

答案 2 :(得分:5)

AmazonS3Client类具有以下方法:

S3Object getObject(String bucketName, String key)

返回的S3Object具有方法...

java.io.InputStream getObjectContent()

..将对象内容作为流获取。我会像Apache Commons一样使用IOUtils:

IOUtils.copy(s3Object.getObjectContent(), new FileOutputStream(new File(filepath)));

答案 3 :(得分:3)

使用TransferManager这个衬管怎么样:

TransferManagerBuilder.defaultTransferManager
  .download("bucket-name", "key", new File("."))

答案 4 :(得分:0)

2017年发布的Java版AWS SDK v2 中,您只需指定Path即可写入文件。

s3.getObject(GetObjectRequest.builder().bucket(bucket).key(key).build(),
        ResponseTransformer.toFile(Paths.get("multiPartKey")));

https://docs.aws.amazon.com/sdk-for-java/v2/developer-guide/examples-s3-objects.html#download-object

如果您需要File,则可以使用toFile方法。

Path path = Paths.get("file.txt");
s3.getObject(GetObjectRequest.builder().bucket(bucket).key(key).build(),
        path);
File file = path.toFile();

答案 5 :(得分:0)

Observable.merge(stream1, stream2)