AWS S3(带 SDK 2.x)- 文件上传到 S3 选项(更少的内存消耗和没有临时文件)可用吗?

问题描述 投票:0回答:1

最近我们决定迁移 Java 文件上传/下载用例,以通过 AWS S3 从我们的旧 SFTP VM 满足需求。我的文件大小通常在 0-10 MB 之间,并且可以有多个并发用户(Java API)上传文件。

这样做的时候,我遇到了 4 个选项,主要是将文件上传到 S3 存储桶。

  • OPTION_1 : Inputstream to byteArray

RequestBody.fromBytes(IoUtils.toByteArray(s3FileObject.getInputStream()));
/// 这会消耗大量内存,因为它将整个流读入 byteArray,然后通过 putObject 写入 S3

  • OPTION_2:作为输入流

RequestBody.fromInputStream(s3FileObject.getInputStream(), s3FileObject.getInputStream().available());
/// 这里我真的没有输入流的大小(因为 s3FileObject.getInputStream().available() 并不总是正确获取输入流的长度)

  • OPTION_3:输入流到文件

RequestBody.fromFile(file)
/// 我真的不想在我的 Java serevr 或临时文件夹上创建临时文件,因为与我们最初通过 SFTP 上传到 VM 的方法相比,这是开销很大。

  • OPTION_4:多部分上传

s3.uploadPart(part,RequestBody.fromBytes(bytes)).eTag();
// 最小部分大小为 5 MB,因此多个用户说 100 个上传这些文件会消耗大量内存。

我之前是如何实施的 我们有 Apach VFS,它用于将输出流打开到 SFTP 文件,我们用于从输入流读取小块并写入 OutputStream(SFTP 中的文件)

示例代码

public long transferStream(InputStream inputStream, OutputStream outputStream) throws IOException
{
    int bytesRead = 0;
    long streamSize = 0;
    byte[] buf = new byte[4 * 1024];
    while ((bytesRead = inputStream.read(buf)) != -1)
    {
        streamSize += bytesRead;
        outputStream.write(buf, 0, bytesRead);
        outputStream.flush();
    }
    outputStream.flush();
    return streamSize;
}
  • 我在这里有2个问题
  1. 有没有办法获取 S3 文件的输出流并像上面那样用小块写入?
  2. 对于具有 4 GB 机器和 2 GB XMX 的应用程序 - 即使我们在上传后删除文件后,临时文件选项(上面的 OPTION_3)如何工作。

有没有更好的方法来处理 S3 上传而没有太多的内存开销和临时文件。

谢谢

java amazon-s3 aws-sdk inputstream fileinputstream
1个回答
© www.soinside.com 2019 - 2024. All rights reserved.