使用 AWS SDK 执行 Amazon S3 对象的分段上传 - Amazon Simple Storage Service

使用 AWS SDK 执行 Amazon S3 对象的分段上传

以下代码示例显示如何执行 Amazon S3 对象的分段上传。

Java
SDK for Java 2.x
注意

查看 GitHub,了解更多信息。例如,如果您将大小为 128 KB 到 1024 KB 的对象设置为从 S3 标准存储类移到 S3标准-IA 存储类,则大小精确为 1024 KB 和 128 KB 的对象将不会转换到 S3 标准-IA。

代码示例使用以下导入。

import org.slf4j.Logger; import org.slf4j.LoggerFactory; import software.amazon.awssdk.core.exception.SdkException; import software.amazon.awssdk.core.sync.RequestBody; import software.amazon.awssdk.services.s3.S3AsyncClient; import software.amazon.awssdk.services.s3.S3Client; import software.amazon.awssdk.services.s3.model.CompletedMultipartUpload; import software.amazon.awssdk.services.s3.model.CompletedPart; import software.amazon.awssdk.services.s3.model.CreateMultipartUploadResponse; import software.amazon.awssdk.services.s3.model.PutObjectResponse; import software.amazon.awssdk.services.s3.model.UploadPartRequest; import software.amazon.awssdk.services.s3.model.UploadPartResponse; import software.amazon.awssdk.services.s3.waiters.S3Waiter; import software.amazon.awssdk.transfer.s3.S3TransferManager; import software.amazon.awssdk.transfer.s3.model.FileUpload; import software.amazon.awssdk.transfer.s3.model.UploadFileRequest; import java.io.IOException; import java.io.RandomAccessFile; import java.net.URISyntaxException; import java.net.URL; import java.nio.ByteBuffer; import java.nio.file.Paths; import java.util.ArrayList; import java.util.List; import java.util.Objects; import java.util.UUID; import java.util.concurrent.CompletableFuture;

基于 AWS CRT 的 S3 客户端上使用 S3 Transfer Manager,以在内容大小超过阈值时透明地执行分段上传。默认阈值大小为 8 MB。

public void multipartUploadWithTransferManager(String filePath) { S3TransferManager transferManager = S3TransferManager.create(); UploadFileRequest uploadFileRequest = UploadFileRequest.builder() .putObjectRequest(b -> b .bucket(bucketName) .key(key)) .source(Paths.get(filePath)) .build(); FileUpload fileUpload = transferManager.uploadFile(uploadFileRequest); fileUpload.completionFuture().join(); transferManager.close(); }

使用 S3Client API 执行分段上传。

public void multipartUploadWithS3Client(String filePath) { // Initiate the multipart upload. CreateMultipartUploadResponse createMultipartUploadResponse = s3Client.createMultipartUpload(b -> b .bucket(bucketName) .key(key)); String uploadId = createMultipartUploadResponse.uploadId(); // Upload the parts of the file. int partNumber = 1; List<CompletedPart> completedParts = new ArrayList<>(); ByteBuffer bb = ByteBuffer.allocate(1024 * 1024 * 5); // 5 MB byte buffer try (RandomAccessFile file = new RandomAccessFile(filePath, "r")) { long fileSize = file.length(); long position = 0; while (position < fileSize) { file.seek(position); long read = file.getChannel().read(bb); bb.flip(); // Swap position and limit before reading from the buffer. UploadPartRequest uploadPartRequest = UploadPartRequest.builder() .bucket(bucketName) .key(key) .uploadId(uploadId) .partNumber(partNumber) .build(); UploadPartResponse partResponse = s3Client.uploadPart( uploadPartRequest, RequestBody.fromByteBuffer(bb)); CompletedPart part = CompletedPart.builder() .partNumber(partNumber) .eTag(partResponse.eTag()) .build(); completedParts.add(part); bb.clear(); position += read; partNumber++; } } catch (IOException e) { logger.error(e.getMessage()); } // Complete the multipart upload. s3Client.completeMultipartUpload(b -> b .bucket(bucketName) .key(key) .uploadId(uploadId) .multipartUpload(CompletedMultipartUpload.builder().parts(completedParts).build())); }

使用启用分段支持的 S3AsyncClient API 执行分段上传。

public void multipartUploadWithS3AsyncClient(String filePath) { // Enable multipart support. S3AsyncClient s3AsyncClient = S3AsyncClient.builder() .multipartEnabled(true) .build(); CompletableFuture<PutObjectResponse> response = s3AsyncClient.putObject(b -> b .bucket(bucketName) .key(key), Paths.get(filePath)); response.join(); logger.info("File uploaded in multiple 8 MiB parts using S3AsyncClient."); }

有关 AWS SDK 开发人员指南和代码示例的完整列表,请参阅 将此服务与 AWS SDK 结合使用。本主题还包括有关入门的信息以及有关先前的 SDK 版本的详细信息。