通过断点续传上传的方式将文件上传到 TOS 前,您可以设置分片大小、上传分片的线程数、上传时客户端限速、事件回调函数等。同时也能在断点续传上传任务执行过程中,取消该任务。若出现网络异常等情况导致文件上传失败时,将从断点记录处继续上传未上传完成的部分。
tos:PutObject
权限,具体操作,请参见权限配置指南。Checkpoint
文件中,所以程序需要对 Checkpoint
文件有写权限。Checkpoint
文件中,如果上传过程中某一分片上传失败,再次上传时会 Checkpoint
文件中记录的点继续上传。上传完成后, Checkpoint
文件会被删除。以下代码用于断点续传上传将本地文件上传到目标桶 examplebucket
中的 exampledir/exampleobject.txt
对象。若上传过程中返回网络超时的报错,则您以相同参数调用 uploadFile 后可实现断点重入上传。
#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"; // 填写本地文件完整路径,例如/localpath/examplefile.txt,其中localpath为本地文件examplefile.txt所在本地路径 std::string filePath = "/localpath/examplefile.txt"; // 记录本地分片上传结果的文件。上传过程中的进度信息会保存在该文件中,如果某一分片上传失败,再次上传时会根据文件中记录的点继续上传。上传完成后,该文件会被删除。 // 如果未设置该值,默认与待上传的本地文件同路径。 std::string CheckpointFilePath = "yourCheckpointFilepath"; // 初始化网络等资源 InitializeClient(); // 创建交互的 client TosClientV2 client(region, accessKey, secretKey); // 断点续传上传 UploadFileV2Input input(bucketName, objectName); // 并发下载分片的线程数 1-1000 input.setTaskNum(10); // 开启 checkpoint 会在本地生成断点续传记录文件 input.setEnableCheckpoint(true); // 默认分片大小 20MB input.setPartSize(20 * 1024 * 1024); // 待上传文件的路径,不可为空,不可为文件夹,建议设置绝对路径 input.setFilePath(filePath); auto output = client.uploadFile(input); if (!output.isSuccess()) { // 异常处理 std::cout << "UploadFile failed." << output.error().String() << std::endl; // 释放网络等资源 CloseClient(); return -1; } std::cout << "UploadFile success. object etag is: " << output.result().getETag() << std::endl; // 释放网络等资源 CloseClient(); return 0; }
以下代码用于配置断点续传上传进度条功能。
#include "TosClientV2.h" using namespace VolcengineTos; static void ProgressCallback(std::shared_ptr<DataTransferStatus> datatransferstatus) { int64_t consumedBytes = datatransferstatus->consumedBytes_; int64_t totalBytes = datatransferstatus->totalBytes_; int64_t rwOnceBytes = datatransferstatus->rwOnceBytes_; DataTransferType type = datatransferstatus->type_; int64_t rate = 100 * consumedBytes / totalBytes; std::cout << "rate:" << rate << "," << "ConsumedBytes:" << consumedBytes << "," << "totalBytes:" << totalBytes << "," << "rwOnceBytes:" << rwOnceBytes << "," << "DataTransferType:" << type << std::endl; } 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"; // 填写本地文件完整路径,例如/localpath/examplefile.txt,其中localpath为本地文件examplefile.txt所在本地路径 std::string filePath = "/localpath/examplefile.txt"; // 记录本地分片上传结果的文件。上传过程中的进度信息会保存在该文件中,如果某一分片上传失败,再次上传时会根据文件中记录的点继续上传。上传完成后,该文件会被删除。 // 如果未设置该值,默认与待上传的本地文件同路径。 std::string CheckpointFilePath = "yourCheckpointFilepath"; // 初始化网络等资源 InitializeClient(); // 创建交互的 client TosClientV2 client(region, accessKey, secretKey); // 断点续传上传 UploadFileV2Input input(bucketName, objectName); // 并发下载分片的线程数 1-1000 input.setTaskNum(10); // 开启 checkpoint 会在本地生成断点续传记录文件 input.setEnableCheckpoint(true); // 默认分片大小 20MB input.setPartSize(20 * 1024 * 1024); // 待上传文件的路径,不可为空,不可为文件夹,建议设置绝对路径 input.setFilePath(filePath); // 设置进度条 DataTransferListener processHandler = {ProgressCallback, nullptr}; input.setDataTransferListener(processHandler); auto output = client.uploadFile(input); if (!output.isSuccess()) { // 异常处理 std::cout << "UploadFile failed." << output.error().String() << std::endl; // 释放网络等资源 CloseClient(); return -1; } std::cout << "UploadFile success. object etag is: " << output.result().getETag() << std::endl; // 释放网络等资源 CloseClient(); return 0; }
uploadFile 接口调用过程会发送初始化分片、上传分片、合并分片等事件,您可以传入自定义接口来监听上传的相关事件,并实现自定义的业务逻辑。以下代码用于展示自定义断点续传上传回调函数功能。
#include "TosClientV2.h" using namespace VolcengineTos; static void UploadCallBack(std::shared_ptr<UploadEvent> event) { UploadEventType type_ = event->type_; bool error_ = event->error_; std::string bucket_ = event->bucket_; std::string key_ = event->key_; std::string fileInfo = bucket_ + key_; std::shared_ptr<std::string> uploadId_ = event->uploadId_; std::shared_ptr<std::string> checkpointFile_ = event->checkpointFile_; std::shared_ptr<UploadPartInfo> uploadPartInfo_ = event->uploadPartInfo_; std::string uploadPartInfo = ""; if (uploadPartInfo_ != nullptr) { uploadPartInfo = std::to_string(uploadPartInfo_->partSize_) + "," + std::to_string(uploadPartInfo_->offset_) + "," + std::to_string(uploadPartInfo_->partNumber_) + "," + *(uploadPartInfo_->eTag_) + "," + std::to_string(*(uploadPartInfo_->hashCrc64ecma_)); } std::cout << "type:" << type_ << "," << "error:"<< error_ << "," << "fileInfo:" << fileInfo << "," << "checkpointFile:" << *checkpointFile_ << "," << "uploadId:" << *uploadId_ << "," << "uploadPartInf:" << uploadPartInfo << std::endl; } 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"; // 填写本地文件完整路径,例如/localpath/examplefile.txt,其中localpath为本地文件examplefile.txt所在本地路径 std::string filePath = "/localpath/examplefile.txt"; // 记录本地分片上传结果的文件。上传过程中的进度信息会保存在该文件中,如果某一分片上传失败,再次上传时会根据文件中记录的点继续上传。上传完成后,该文件会被删除。 // 如果未设置该值,默认与待上传的本地文件同路径。 std::string CheckpointFilePath = "yourCheckpointFilepath"; // 初始化网络等资源 InitializeClient(); // 创建交互的 client TosClientV2 client(region, accessKey, secretKey); // 断点续传上传 UploadFileV2Input input(bucketName, objectName); // 并发下载分片的线程数 1-1000 input.setTaskNum(10); // 开启 checkpoint 会在本地生成断点续传记录文件 input.setEnableCheckpoint(true); // 默认分片大小 20MB input.setPartSize(20 * 1024 * 1024); // 待上传文件的路径,不可为空,不可为文件夹,建议设置绝对路径 input.setFilePath(filePath); // 设置 UploadEvent UploadEventListener uploadHandler = {UploadCallBack}; input.setUploadEventListener(uploadHandler); auto output = client.uploadFile(input); if (!output.isSuccess()) { // 异常处理 std::cout << "UploadFile failed." << output.error().String() << std::endl; // 释放网络等资源 CloseClient(); return -1; } std::cout << "UploadFile success. object etag is: " << output.result().getETag() << std::endl; // 释放网络等资源 CloseClient(); return 0; }
以下代码用于设置断点续传上传客户端限速。
#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"; // 填写本地文件完整路径,例如/localpath/examplefile.txt,其中localpath为本地文件examplefile.txt所在本地路径 std::string filePath = "/localpath/examplefile.txt"; // 记录本地分片上传结果的文件。上传过程中的进度信息会保存在该文件中,如果某一分片上传失败,再次上传时会根据文件中记录的点继续上传。上传完成后,该文件会被删除。 // 如果未设置该值,默认与待上传的本地文件同路径。 std::string CheckpointFilePath = "yourCheckpointFilepath"; // 初始化网络等资源 InitializeClient(); // 创建交互的 client TosClientV2 client(region, accessKey, secretKey); // 断点续传上传 UploadFileV2Input input(bucketName, objectName); // 并发下载分片的线程数 1-1000 input.setTaskNum(10); // 开启 checkpoint 会在本地生成断点续传记录文件 input.setEnableCheckpoint(true); // 默认分片大小 20MB input.setPartSize(20 * 1024 * 1024); // 待上传文件的路径,不可为空,不可为文件夹,建议设置绝对路径 input.setFilePath(filePath); // 设置 rateLimiter std::shared_ptr<RateLimiter> RateLimiter(NewRateLimiter(20 * 1024 * 1024, 5 * 1024 * 1024)); input.setRateLimiter(RateLimiter); auto output = client.uploadFile(input); if (!output.isSuccess()) { // 异常处理 std::cout << "UploadFile failed." << output.error().String() << std::endl; // 释放网络等资源 CloseClient(); return -1; } std::cout << "UploadFile success. object etag is: " << output.result().getETag() << std::endl; // 释放网络等资源 CloseClient(); return 0; }
uploadFile 接口支持您主动暂停或取消断点续传任务。暂停断点续传任务会停止上传,再次调用 uploadFile 时可以从上次暂停的位置继续上传。取消断点续传任务会停止上传,删除本地的 CheckPoint 文件,并调用 abortMultipartUpload 来删除分片上传任务,再次调用 uploadFile 时会重新开始上传。
以下代码展示如何暂停或取消断点续传。
#include "TosClientV2.h" #include <thread> using namespace VolcengineTos; static void threadFunction1(TosClientV2 client, UploadFileV2Input input) { auto output = client.uploadFile(input); if (!output.isSuccess()) { std::cout << "UploadFile failed." << output.error().String() << std::endl; } std::cout << "UploadFile success. object etag is: " << output.result().getETag() << std::endl; } static void threadFunction2(std::shared_ptr<CancelHook> CancelHook) { // false 代表不清除 checkpoint 等信息。true 代表清除 checkpoint 等信息 CancelHook->Cancel(false); } 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"; // 填写本地文件完整路径,例如/localpath/examplefile.txt,其中localpath为本地文件examplefile.txt所在本地路径 std::string filePath = "/localpath/examplefile.txt"; // 记录本地分片上传结果的文件。上传过程中的进度信息会保存在该文件中,如果某一分片上传失败,再次上传时会根据文件中记录的点继续上传。上传完成后,该文件会被删除。 // 如果未设置该值,默认与待上传的本地文件同路径。 std::string CheckpointFilePath = "yourCheckpointFilepath"; // 初始化网络等资源 InitializeClient(); // 创建交互的 client TosClientV2 client(region, accessKey, secretKey); // 断点续传上传 UploadFileV2Input input(bucketName, objectName); // 并发下载分片的线程数 1-1000 input.setTaskNum(10); // 开启 checkpoint 会在本地生成断点续传记录文件 input.setEnableCheckpoint(true); // 默认分片大小 20MB input.setPartSize(20 * 1024 * 1024); // 待上传文件的路径,不可为空,不可为文件夹,建议设置绝对路径 input.setFilePath(filePath); // 设置 cancelHook std::shared_ptr<CancelHook> CancelHook(NewCancelHook()); input.setCancelHook(CancelHook); // 线程1中执行断点续传上传接口 std::thread thread1(threadFunction1, client, input); thread1.detach(); TimeUtils::sleepSecondTimes(5); // 运行五秒后在线程2中中断该次请求 std::thread thread2(threadFunction2, CancelHook); thread1.join(); thread2.join(); // 释放网络等资源 CloseClient(); return 0; }