对于较大的对象,可以分成多个数据块(part)来分别上传,最后调用合并分片将上传的数据块合并为一个对象。
tos:PutObject
权限,具体操作,请参见权限配置指南。tos:AbortMultipartUpload
权限,具体操作,请参见权限配置指南。分片上传一般包含以下三个步骤:
说明
以下代码通过分片上传将本地文件上传到目标桶 examplebucket
中的 exampledir/exampleobject.txt
对象。并在上传时指定 ACL 为 PublicRead、存储类型为低频存储以及添加自定义元数据。
#include "TosClientV2.h" using namespace VolcengineTos; static int64_t getFileSize(const std::string& file) { std::fstream f(file, std::ios::in | std::ios::binary); f.seekg(0, f.end); int64_t size = f.tellg(); f.close(); return size; } int main(void){ // 初始化 TOS 账号信息 // Your Region 填写 Bucket 所在 Region std::string region = "Your Region"; std::string accessKey = std::getenv("TOS_ACCESS_KEY"); std::string secretKey = std::getenv("TOS_SECRET_KEY"); // 填写 Bucket 名称,例如 examplebucket std::string bucketName = "examplebucket"; // 填写Object完整路径,完整路径中不能包含Bucket名称,例如exampledir/exampleobject.txt。 std::string objectName = "exampledir/exampleobject.txt"; // 初始化网络等资源 InitializeClient(); // 创建交互的 client TosClientV2 client(region, accessKey, secretKey); // 初始化分片上传事件 CreateMultipartUploadInput input(bucketName, objectName); // 可以指定 ACL,StorageClass,用户自定义元数据等 input.setAcl(ACLType::PublicRead); input.setStorageClass(StorageClassType::IA); input.setMeta({{"self-test", "yes"}}); auto upload = client.createMultipartUpload(input); if (!upload.isSuccess()) { // 异常处理 std::cout << "createMultipartUpload failed." << upload.error().String() << std::endl; // 释放网络等资源 CloseClient(); return -1; } std::cout << "createMultipartUpload success." << std::endl; // 准备上传的文件 std::string fileToUpload = "yourLocalFilename"; // 5MB int64_t partSize = 5 * 1024 * 1024; std::vector<UploadedPartV2> partResList; auto fileSize = getFileSize(fileToUpload); int partCount = static_cast<int>(fileSize / partSize); // 计算分片个数 if (fileSize % partSize != 0) { partCount++; } // 对每一个分片进行上传 auto uploadId = upload.result().getUploadId(); for (int i = 1; i <= partCount; i++) { auto offset = partSize * (i - 1); auto size = (partSize < fileSize - offset) ? partSize : (fileSize - offset); std::shared_ptr<std::iostream> content = std::make_shared<std::fstream>(fileToUpload, std::ios::in|std::ios::binary); content->seekg(offset, std::ios::beg); UploadPartV2Input uploadPartInput(bucketName, objectName,uploadId, size,i,content); auto uploadPartOutput = client.uploadPart(uploadPartInput); if (!uploadPartOutput.isSuccess()) { std::cout << "uploadPart failed." << upload.error().String() << std::endl; // 释放网络等资源 CloseClient(); return -1; } UploadedPartV2 part(i, uploadPartOutput.result().getETag()); partResList.push_back(part); } // 完成分片上传 CompleteMultipartUploadV2Input completeMultipartUploadInput(bucketName, objectName, uploadId, partResList); auto com = client.completeMultipartUpload(completeMultipartUploadInput); if (!com.isSuccess()) { // 异常处理 std::cout << "CompleteMultipartUpload failed." << upload.error().String() << std::endl; // 释放网络等资源 CloseClient(); return -1; } std::cout << "CompleteMultipartUpload success." << com.result().getRequestInfo().getRequestId() << std::endl; // 释放网络等资源 CloseClient(); return 0; }
以下代码用于列举桶 examplebucket
中对象 exampledir/exampleobject.txt
已上传的分片信息。
#include "TosClientV2.h" using namespace VolcengineTos; int main(void){ // 初始化 TOS 账号信息 // Your Region 填写 Bucket 所在 Region。 std::string region = "Your Region"; std::string accessKey = std::getenv("TOS_ACCESS_KEY"); std::string secretKey = std::getenv("TOS_SECRET_KEY"); // 填写 Bucket 名称,例如 examplebucket。 std::string bucketName = "examplebucket"; // 填写Object完整路径,完整路径中不能包含Bucket名称,例如exampledir/exampleobject.txt。 std::string objectName = "exampledir/exampleobject.txt"; // 填写UploadId,例如 f93f6fc9da94371f321e1008。uploadId来自于CreateMultipartUploadInput返回的结果。 std::string uploadId = "f93f6fc9da94371f321e1008"; // 初始化网络等资源 InitializeClient(); // 创建交互的 client TosClientV2 client(region, accessKey, secretKey); // 列举已上传分片,默认列举1000个分片 ListPartsInput input(bucketName,objectName,uploadId); // 设置返回分片上传任务的最大数量。 input.setMaxParts(100); // 指定分片号的起始位置,只列举分片号大于此值的段,以 1 为例子。 input.setPartNumberMarker(1); auto output = client.listParts(input); if (!output.isSuccess()) { // 异常处理 std::cout << "ListParts failed." << output.error().String() << std::endl; // 释放网络等资源 CloseClient(); return -1; } std::cout << "ListParts success." << std::endl; for (const auto& part : output.result().getParts()) { std::cout << "part"<< ",partNumber:" << part.getPartNumber() << ",eTag:" << part.getETag() << ",size:" << part.getSize() << ",lastModified time:" << part.getStringFormatLastModified() << std::endl; } // 释放网络等资源 CloseClient(); return 0; }
您可以通过 abortMultipartUpload 方法来取消分片上传任务。当一个分片任务被取消后, TOS 会将已上传的分片数据删除,同时您无法再对此分片任务进行任何操作。
以下代码用于取消桶 examplebucket
中对象 exampledir/exampleobject.txt
的分片上传任务。
#include "TosClientV2.h" using namespace VolcengineTos; int main(void){ int UploadObjectSample::AbortMultipartUpload(){ // 初始化 TOS 账号信息 // Your Region 填写 Bucket 所在 Region。 std::string region = "Your Region"; std::string accessKey = std::getenv("TOS_ACCESS_KEY"); std::string secretKey = std::getenv("TOS_SECRET_KEY"); // 填写 Bucket 名称,例如 examplebucket。 std::string bucketName = "examplebucket"; // 填写Object完整路径,完整路径中不能包含Bucket名称,例如exampledir/exampleobject.txt。 std::string objectName = "exampledir/exampleobject.txt"; // 填写UploadId,例如 f93f6fc9da94371f321e1008。uploadId来自于CreateMultipartUploadInput返回的结果。 std::string uploadId = "f93f6fc9da94371f321e1008"; // 初始化网络等资源 InitializeClient(); // 创建交互的 client TosClientV2 client(region, accessKey, secretKey); // 列举已上传分片,默认列举1000个分片 AbortMultipartUploadInput input(bucketName,objectName,uploadId); auto output = client.abortMultipartUpload(input); if (!output.isSuccess()) { // 异常处理 std::cout << "AbortMultipartUpload failed." << output.error().String() << std::endl; // 释放网络等资源 CloseClient(); return -1; } std::cout << "AbortMultipartUpload success." << std::endl; // 释放网络等资源 CloseClient(); return 0; }