【问题标题】:Multipart Upload Amazon S3分段上传 Amazon S3
【发布时间】:2014-10-14 09:41:49
【问题描述】:

我正在尝试使用他们的 API 在 Amazon S3 上上传文件。我尝试使用他们的示例代码,它创建了文件的各个部分。现在,问题是,我如何暂停上传然后恢复它?请参阅其文档中给出的以下代码:

import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;

import com.amazonaws.auth.profile.ProfileCredentialsProvider;
import com.amazonaws.services.s3.AmazonS3;
import com.amazonaws.services.s3.AmazonS3Client;
import com.amazonaws.services.s3.model.AbortMultipartUploadRequest;
import com.amazonaws.services.s3.model.CompleteMultipartUploadRequest;
import com.amazonaws.services.s3.model.InitiateMultipartUploadRequest;
import com.amazonaws.services.s3.model.InitiateMultipartUploadResult;
import com.amazonaws.services.s3.model.PartETag;
import com.amazonaws.services.s3.model.UploadPartRequest;

public class UploadObjectMPULowLevelAPI {

public static void main(String[] args) throws IOException {
    String existingBucketName  = "*** Provide-Your-Existing-BucketName ***"; 
    String keyName             = "*** Provide-Key-Name ***";
    String filePath            = "*** Provide-File-Path ***";   

    AmazonS3 s3Client = new AmazonS3Client(new ProfileCredentialsProvider());        

    // Create a list of UploadPartResponse objects. You get one of these
    // for each part upload.
    List<PartETag> partETags = new ArrayList<PartETag>();

    // Step 1: Initialize.
    InitiateMultipartUploadRequest initRequest = new 
         InitiateMultipartUploadRequest(existingBucketName, keyName);
    InitiateMultipartUploadResult initResponse = 
                           s3Client.initiateMultipartUpload(initRequest);

    File file = new File(filePath);
    long contentLength = file.length();
    long partSize = 5242880; // Set part size to 5 MB.

    try {
        // Step 2: Upload parts.
        long filePosition = 0;
        for (int i = 1; filePosition < contentLength; i++) {
            // Last part can be less than 5 MB. Adjust part size.
            partSize = Math.min(partSize, (contentLength - filePosition));

            // Create request to upload a part.
            UploadPartRequest uploadRequest = new UploadPartRequest()
                .withBucketName(existingBucketName).withKey(keyName)
                .withUploadId(initResponse.getUploadId()).withPartNumber(i)
                .withFileOffset(filePosition)
                .withFile(file)
                .withPartSize(partSize);

            // Upload part and add response to our list.
            partETags.add(
                    s3Client.uploadPart(uploadRequest).getPartETag());

            filePosition += partSize;
        }

        // Step 3: Complete.
        CompleteMultipartUploadRequest compRequest = new 
                     CompleteMultipartUploadRequest(
                                existingBucketName, 
                                keyName, 
                                initResponse.getUploadId(), 
                                partETags);

        s3Client.completeMultipartUpload(compRequest);
    } 
    catch (Exception e) 
    {
        s3Client.abortMultipartUpload(new AbortMultipartUploadRequest(
                existingBucketName, keyName, initResponse.getUploadId()));
    }
}
}

我还尝试了 TransferManager 示例,该示例采用 Upload 对象并调用 tryPause(forceCancel) 方法。但这里的问题是,每次我尝试暂停它时它都会被取消。

我的问题是,如何使用上面的代码和暂停和恢复功能?另外,请注意,我还想上传具有相同功能的多个文件....帮助将不胜感激。

【问题讨论】:

    标签: file-upload amazon-web-services amazon-s3 file-transfer


    【解决方案1】:

    TransferManager 异步执行上传和下载,不会阻塞当前线程。当您调用resumeUpload 时,TransferManager 立即返回对Upload 的引用。您可以使用此参考来查询上传的状态。

    【讨论】:

      【解决方案2】:

      如果可以,我认为您应该使用 Transfer Manager 示例。如果它被取消,则很可能无法暂停它(使用您正在使用的 TransferManager 的给定配置)。

      这可能是因为您过早地暂停以使“暂停”意味着除取消之外的任何其他内容,您正在尝试使用加密,或者文件不够大。我相信默认的最小文件大小是 16MB。但是,您可以更改 TransferManager 的配置以允许您根据 tryPause 失败而暂停,除非在加密的情况下我认为您无能为力。

      如果要为小于该大小的文件启用暂停/恢复,可以调用 TransferManagerConfiguration 中的 setMultipartUploadThreshold(long) 方法。如果您希望能够提前暂停,可以使用 setMinimumUploadPartSize 将其设置为使用较小的块。

      无论如何,如果可能,我建议您使用 TransferManager,因为它是为您做这种事情的。当您使用 tryPause 时,了解传输未暂停的原因可能会有所帮助。

      【讨论】:

      • 感谢您的回复。我尝试了这种方法,但现在它没有恢复上传(java.awsblog.com/post/Tx2Y9J2CUDVJ5LZ/…)。以下是不工作的步骤: 1. 一旦来自persistable Upload 的信息被序列化到一个文件中,当数据被检索和反序列化时,我调用方法 transferManager.resumeUpload(persistableUpload);这不会出错,但不会做任何事情。
      猜你喜欢
      • 2017-08-23
      • 1970-01-01
      • 1970-01-01
      • 2014-06-14
      • 2015-06-25
      • 2012-11-01
      • 1970-01-01
      • 2011-07-21
      • 2023-03-14
      相关资源
      最近更新 更多