C++客戶端加密
本文中含有需要您注意的重要提示信息,忽略該信息可能對(duì)您的業(yè)務(wù)造成影響,請(qǐng)務(wù)必仔細(xì)閱讀。
OSS客戶端加密是在數(shù)據(jù)上傳至OSS之前,由用戶在本地對(duì)數(shù)據(jù)進(jìn)行加密處理,確保只有密鑰持有者才能解密數(shù)據(jù),增強(qiáng)數(shù)據(jù)在傳輸和存儲(chǔ)過程中的安全性。
免責(zé)聲明
使用客戶端加密功能時(shí),您需要對(duì)主密鑰的完整性和正確性負(fù)責(zé)。因您維護(hù)不當(dāng)導(dǎo)致主密鑰用錯(cuò)或丟失,從而導(dǎo)致加密數(shù)據(jù)無法解密所引起的一切損失和后果均由您自行承擔(dān)。
在對(duì)加密數(shù)據(jù)進(jìn)行復(fù)制或者遷移時(shí),您需要對(duì)加密元數(shù)據(jù)的完整性和正確性負(fù)責(zé)。因您維護(hù)不當(dāng)導(dǎo)致加密元數(shù)據(jù)出錯(cuò)或丟失,從而導(dǎo)致加密數(shù)據(jù)無法解密所引起的一切損失和后果均由您自行承擔(dān)。
使用場景
高度敏感數(shù)據(jù):對(duì)于包含極高敏感度信息的數(shù)據(jù),如個(gè)人身份信息(PII)、金融交易記錄、醫(yī)療健康數(shù)據(jù)等,用戶可能希望在數(shù)據(jù)離開本地環(huán)境之前就對(duì)其進(jìn)行加密處理,確保即使數(shù)據(jù)在傳輸過程中被截獲,原始數(shù)據(jù)仍能得到有效保護(hù)。
合規(guī)要求:某些行業(yè)和法規(guī)(例如HIPAA、GDPR等)要求對(duì)存儲(chǔ)在第三方平臺(tái)上的數(shù)據(jù)進(jìn)行嚴(yán)格的加密控制,客戶端加密能夠滿足這些合規(guī)性要求,因?yàn)槊荑€由用戶自己管理,不通過網(wǎng)絡(luò)傳遞,也不由云服務(wù)商直接掌握。
更強(qiáng)的自主控制權(quán):企業(yè)或者開發(fā)者可能希望對(duì)加密過程有完全的控制權(quán),包括選擇加密算法、管理和輪換密鑰。通過客戶端加密,可以實(shí)現(xiàn)這一目標(biāo),確保只有合法授權(quán)的用戶才能解密和訪問數(shù)據(jù)。
跨區(qū)域數(shù)據(jù)遷移安全性:在將數(shù)據(jù)從一個(gè)地區(qū)遷移到另一個(gè)地區(qū)的過程中,使用客戶端加密可以在數(shù)據(jù)遷移前后保持?jǐn)?shù)據(jù)始終處于加密狀態(tài),增強(qiáng)了數(shù)據(jù)在公網(wǎng)傳輸?shù)陌踩浴?/p>
注意事項(xiàng)
本文以華東1(杭州)外網(wǎng)Endpoint為例。如果您希望通過與OSS同地域的其他阿里云產(chǎn)品訪問OSS,請(qǐng)使用內(nèi)網(wǎng)Endpoint。關(guān)于OSS支持的Region與Endpoint的對(duì)應(yīng)關(guān)系,請(qǐng)參見OSS地域和訪問域名。
本文以OSS域名新建OSSClient為例。如果您希望通過自定義域名、STS等方式新建OSSClient,請(qǐng)參見新建OssClient。
背景信息
使用客戶端加密時(shí),會(huì)為每個(gè)Object生成一個(gè)隨機(jī)數(shù)據(jù)加密密鑰,用該隨機(jī)數(shù)據(jù)加密密鑰明文對(duì)Object的數(shù)據(jù)進(jìn)行對(duì)稱加密。主密鑰用于生成隨機(jī)的數(shù)據(jù)加密密鑰,加密后的內(nèi)容會(huì)作為Object的meta信息保存在服務(wù)端。解密時(shí)先用主密鑰將加密后的隨機(jī)密鑰解密出來,再用解密出來的隨機(jī)數(shù)據(jù)加密密鑰明文解密Object的數(shù)據(jù)。主密鑰只參與客戶端本地計(jì)算,不會(huì)在網(wǎng)絡(luò)上進(jìn)行傳輸或保存在服務(wù)端,以保證主密鑰的數(shù)據(jù)安全。
客戶端加密支持分片上傳超過5 GB的文件。在使用分片方式上傳文件時(shí),需要指定上傳文件的總大小和分片大小, 除了最后一個(gè)分片外,每個(gè)分片的大小要一致,且分片大小目前必須是16的整數(shù)倍。
調(diào)用客戶端加密上傳文件后,加密元數(shù)據(jù)會(huì)被保護(hù),無法通過CopyObject修改Object meta信息。
加密方式
對(duì)于主密鑰的使用,目前支持如下兩種方式:
使用KMS托管用戶主密鑰
當(dāng)使用KMS托管用戶主密鑰用于客戶端數(shù)據(jù)加密時(shí),需要將KMS用戶主密鑰ID(即CMK ID)傳遞給SDK。
使用用戶自主管理的主密鑰(RSA)
主密鑰信息由用戶提供,需要用戶將主密鑰的公鑰、私鑰信息作為參數(shù)傳遞給SDK。
使用以上兩種加密方式能夠有效地避免數(shù)據(jù)泄漏,保護(hù)客戶端數(shù)據(jù)安全。即使數(shù)據(jù)泄漏,其他人也無法解密得到原始數(shù)據(jù)。
加密元數(shù)據(jù)
參數(shù) | 描述 | 是否必需 |
x-oss-meta-client-side-encryption-key | 加密后的密鑰。經(jīng)過主密鑰加密后再經(jīng)過base64編碼的字符串。 | 是 |
x-oss-meta-client-side-encryption-start | 隨機(jī)產(chǎn)生的加密數(shù)據(jù)的初始值。經(jīng)過主密鑰加密后再經(jīng)過base64編碼的字符串。 | 是 |
x-oss-meta-client-side-encryption-cek-alg | 數(shù)據(jù)的加密算法。 | 是 |
x-oss-meta-client-side-encryption-wrap-alg | 數(shù)據(jù)密鑰的加密算法。 | 是 |
x-oss-meta-client-side-encryption-matdesc | 主密鑰的描述信息。JSON格式。 警告 強(qiáng)烈建議為每個(gè)主密鑰都配置描述信息,并保存好主密鑰和描述信息之間的對(duì)應(yīng)關(guān)系。否則不支持更換主密鑰進(jìn)行加密。 | 否 |
x-oss-meta-client-side-encryption-unencrypted-content-length | 加密前的數(shù)據(jù)長度。如未指定content-length則不生成該參數(shù)。 | 否 |
x-oss-meta-client-side-encryption-unencrypted-content-md5 | 加密前數(shù)據(jù)的MD5。如未指定MD5,則不生成該參數(shù)。 | 否 |
x-oss-meta-client-side-encryption-data-size | 若加密Multipart文件需要在init_multipart時(shí)傳入整個(gè)大文件的總大小。 | 是(分片上傳) |
x-oss-meta-client-side-encryption-part-size | 若加密Multipart文件需要在init_multipart時(shí)傳入分片大小。 說明 目前分片大小必須是16的整數(shù)倍。 | 是(分片上傳) |
以下提供了如何使用用戶自主管理的主密鑰(RSA)方式從內(nèi)存中上傳文件、上傳本地文件、斷點(diǎn)續(xù)傳上傳、分片上傳、下載到本地文件等場景的完整示例代碼。
從內(nèi)存中上傳文件
以下代碼用于使用主密鑰RSA加密內(nèi)存中上傳的文件:
#include <alibabacloud/oss/OssEncryptionClient.h>
using namespace AlibabaCloud::OSS;
int main(void)
{
/* 初始化OSS賬號(hào)信息。*/
/* yourEndpoint填寫B(tài)ucket所在地域?qū)?yīng)的Endpoint。以華東1(杭州)為例,Endpoint填寫為https://oss-cn-hangzhou.aliyuncs.com。*/
std::string Endpoint = "yourEndpoint";
/* yourRegion填寫B(tài)ucket所在地域?qū)?yīng)的Region。以華東1(杭州)為例,Region填寫為cn-hangzhou。*/
std::string Region = "yourRegion";
/* 填寫B(tài)ucket名稱,例如examplebucket。*/
std::string BucketName = "examplebucket";
/* 填寫Object完整路徑,完整路徑中不能包含Bucket名稱,例如exampledir/exampleobject.txt。*/
std::string ObjectName = "exampledir/exampleobject.txt";
/* 主密鑰及描述信息。*/
std::string RSAPublicKey = "your rsa public key";
std::string RSAPrivateKey = "your rsa private key";
std::map<std::string, std::string> desc;
desc["comment"] = "your comment";
/* 初始化網(wǎng)絡(luò)等資源。*/
InitializeSdk();
ClientConfiguration conf;
conf.signatureVersion = SignatureVersionType::V4;
/* 從環(huán)境變量中獲取訪問憑證。運(yùn)行本代碼示例之前,請(qǐng)確保已設(shè)置環(huán)境變量OSS_ACCESS_KEY_ID和OSS_ACCESS_KEY_SECRET。*/
auto credentialsProvider = std::make_shared<EnvironmentVariableCredentialsProvider>();
OssClient client(Endpoint, credentialsProvider, conf);
client.SetRegion(Region);
CryptoConfiguration cryptoConf;
auto materials = std::make_shared<SimpleRSAEncryptionMaterials>(RSAPublicKey, RSAPrivateKey, desc);
OssEncryptionClient client(Endpoint, credentialsProvider, conf, materials, cryptoConf);
std::shared_ptr<std::iostream> content = std::make_shared<std::stringstream>();
*content << "Thank you for using Aliyun Object Storage Service!";
PutObjectRequest request(BucketName, ObjectName, content);
/* 上傳文件。*/
auto outcome = client.PutObject(request);
if (!outcome.isSuccess()) {
/* 異常處理。*/
std::cout << "PutObject fail" <<
",code:" << outcome.error().Code() <<
",message:" << outcome.error().Message() <<
",requestId:" << outcome.error().RequestId() << std::endl;
return -1;
}
/* 釋放網(wǎng)絡(luò)等資源。*/
ShutdownSdk();
return 0;
}
上傳本地文件
以下代碼用于使用主密鑰RSA加密本地上傳的文件:
#include <alibabacloud/oss/OssEncryptionClient.h>
using namespace AlibabaCloud::OSS;
int main(void)
{
/* 初始化OSS賬號(hào)信息。*/
/* yourEndpoint填寫B(tài)ucket所在地域?qū)?yīng)的Endpoint。以華東1(杭州)為例,Endpoint填寫為https://oss-cn-hangzhou.aliyuncs.com。*/
std::string Endpoint = "yourEndpoint";
/* yourRegion填寫B(tài)ucket所在地域?qū)?yīng)的Region。以華東1(杭州)為例,Region填寫為cn-hangzhou。*/
std::string Region = "yourRegion";
/* 填寫B(tài)ucket名稱,例如examplebucket。*/
std::string BucketName = "examplebucket";
/* 填寫Object完整路徑,完整路徑中不能包含Bucket名稱,例如exampledir/exampleobject.txt。*/
std::string ObjectName = "exampledir/exampleobject.txt";
/* 主密鑰及描述信息。*/
std::string RSAPublicKey = "your rsa public key";
std::string RSAPrivateKey = "your rsa private key";
std::map<std::string, std::string> desc;
desc["comment"] = "your comment";
/* 初始化網(wǎng)絡(luò)等資源。*/
InitializeSdk();
ClientConfiguration conf;
conf.signatureVersion = SignatureVersionType::V4;
/* 從環(huán)境變量中獲取訪問憑證。運(yùn)行本代碼示例之前,請(qǐng)確保已設(shè)置環(huán)境變量OSS_ACCESS_KEY_ID和OSS_ACCESS_KEY_SECRET。*/
auto credentialsProvider = std::make_shared<EnvironmentVariableCredentialsProvider>();
OssClient client(Endpoint, credentialsProvider, conf);
client.SetRegion(Region);
CryptoConfiguration cryptoConf;
auto materials = std::make_shared<SimpleRSAEncryptionMaterials>(RSAPublicKey, RSAPrivateKey, desc);
OssEncryptionClient client(Endpoint, credentialsProvider, conf, materials, cryptoConf);
/* 上傳文件。*/
auto outcome = client.PutObject(BucketName, ObjectName, "yourLocalFilename");
if (!outcome.isSuccess()) {
/* 異常處理。*/
std::cout << "PutObject fail" <<
",code:" << outcome.error().Code() <<
",message:" << outcome.error().Message() <<
",requestId:" << outcome.error().RequestId() << std::endl;
return -1;
}
/* 釋放網(wǎng)絡(luò)等資源。*/
ShutdownSdk();
return 0;
}
斷點(diǎn)續(xù)傳上傳
以下代碼用于使用主密鑰RSA加密斷點(diǎn)續(xù)傳上傳的文件:
#include <alibabacloud/oss/OssEncryptionClient.h>
using namespace AlibabaCloud::OSS;
int main(void)
{
/* 初始化OSS賬號(hào)信息。*/
/* yourEndpoint填寫B(tài)ucket所在地域?qū)?yīng)的Endpoint。以華東1(杭州)為例,Endpoint填寫為https://oss-cn-hangzhou.aliyuncs.com。*/
std::string Endpoint = "yourEndpoint";
/* yourRegion填寫B(tài)ucket所在地域?qū)?yīng)的Region。以華東1(杭州)為例,Region填寫為cn-hangzhou。*/
std::string Region = "yourRegion";
/* 填寫B(tài)ucket名稱,例如examplebucket。*/
std::string BucketName = "examplebucket";
/* 填寫Object的完整路徑,完整路徑中不能包含Bucket名稱,例如exampledir/exampleobject.txt。*/
std::string ObjectName = "exampledir/exampleobject.txt";
/* 填寫本地文件的完整路徑,例如D:\\localpath\\examplefile.txt。如果未指定本地路徑,則默認(rèn)從示例程序所屬項(xiàng)目對(duì)應(yīng)本地路徑中上傳文件。*/
std::string UploadFilePath = "D:\\localpath\\examplefile.txt";
/* 記錄本地分片上傳結(jié)果的文件。上傳過程中的進(jìn)度信息會(huì)保存在該文件中,如果某一分片上傳失敗,再次上傳時(shí)會(huì)根據(jù)文件中記錄的點(diǎn)繼續(xù)上傳。上傳完成后,該文件會(huì)被刪除。*/
/* 如果未設(shè)置該值,默認(rèn)與待上傳的本地文件同路徑。*/
std::string CheckpointFilePath = "yourCheckpointFilepath"
/* 主密鑰及描述信息。*/
std::string RSAPublicKey = "your rsa public key";
std::string RSAPrivateKey = "your rsa private key";
std::map<std::string, std::string> desc;
desc["comment"] = "your comment";
/* 初始化網(wǎng)絡(luò)等資源。*/
InitializeSdk();
ClientConfiguration conf;
conf.signatureVersion = SignatureVersionType::V4;
/* 從環(huán)境變量中獲取訪問憑證。運(yùn)行本代碼示例之前,請(qǐng)確保已設(shè)置環(huán)境變量OSS_ACCESS_KEY_ID和OSS_ACCESS_KEY_SECRET。*/
auto credentialsProvider = std::make_shared<EnvironmentVariableCredentialsProvider>();
OssClient client(Endpoint, credentialsProvider, conf);
client.SetRegion(Region);
CryptoConfiguration cryptoConf;
auto materials = std::make_shared<SimpleRSAEncryptionMaterials>(RSAPublicKey, RSAPrivateKey, desc);
OssEncryptionClient client(Endpoint, credentialsProvider, conf, materials, cryptoConf);
/* 斷點(diǎn)續(xù)傳上傳。*/
UploadObjectRequest request(BucketName, ObjectName, UploadFilePath, CheckpointFilePath);
auto outcome = client.ResumableUploadObject(request);
if (!outcome.isSuccess()) {
/* 異常處理。*/
std::cout << "ResumableUploadObject fail" <<
",code:" << outcome.error().Code() <<
",message:" << outcome.error().Message() <<
",requestId:" << outcome.error().RequestId() << std::endl;
return -1;
}
/* 釋放網(wǎng)絡(luò)等資源。*/
ShutdownSdk();
return 0;
}
分片上傳
以下代碼用于使用主密鑰RSA加密分片上傳的文件:
#include <alibabacloud/oss/OssEncryptionClient.h>
#include <fstream>
using namespace AlibabaCloud::OSS;
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)
{
/* 初始化OSS賬號(hào)信息。*/
/* yourEndpoint填寫B(tài)ucket所在地域?qū)?yīng)的Endpoint。以華東1(杭州)為例,Endpoint填寫為https://oss-cn-hangzhou.aliyuncs.com。*/
std::string Endpoint = "yourEndpoint";
/* yourRegion填寫B(tài)ucket所在地域?qū)?yīng)的Region。以華東1(杭州)為例,Region填寫為cn-hangzhou。*/
std::string Region = "yourRegion";
/* 填寫B(tài)ucket名稱,例如examplebucket。*/
std::string BucketName = "examplebucket";
/* 填寫Object的完整路徑,完整路徑中不能包含Bucket名稱,例如exampledir/exampleobject.txt。*/
std::string ObjectName = "exampledir/exampleobject.txt";
std::string fileToUpload = "yourLocalFilename";
/* 主密鑰及描述信息。*/
std::string RSAPublicKey = "your rsa public key";
std::string RSAPrivateKey = "your rsa private key";
std::map<std::string, std::string> desc;
desc["comment"] = "your comment";
/* 初始化網(wǎng)絡(luò)等資源。*/
InitializeSdk();
ClientConfiguration conf;
conf.signatureVersion = SignatureVersionType::V4;
/* 從環(huán)境變量中獲取訪問憑證。運(yùn)行本代碼示例之前,請(qǐng)確保已設(shè)置環(huán)境變量OSS_ACCESS_KEY_ID和OSS_ACCESS_KEY_SECRET。*/
auto credentialsProvider = std::make_shared<EnvironmentVariableCredentialsProvider>();
OssClient client(Endpoint, credentialsProvider, conf);
client.SetRegion(Region);
CryptoConfiguration cryptoConf;
auto materials = std::make_shared<SimpleRSAEncryptionMaterials>(RSAPublicKey, RSAPrivateKey, desc);
OssEncryptionClient client(Endpoint, credentialsProvider, conf, materials, cryptoConf);
/* 初始化分片加密上下文。*/
/* 需要16字節(jié)對(duì)齊。*/
int64_t partSize = 100 * 1024;
auto fileSize = getFileSize(fileToUpload);
MultipartUploadCryptoContext cryptoCtx;
cryptoCtx.setPartSize(partSize);
cryptoCtx.setDataSize(fileSize);
/* 初始化分片上傳事件。*/
InitiateMultipartUploadRequest initUploadRequest(BucketName, ObjectName);
auto uploadIdResult = client.InitiateMultipartUpload(initUploadRequest, cryptoCtx);
auto uploadId = uploadIdResult.result().UploadId();
PartList partETagList;
int partCount = static_cast<int> (fileSize / partSize);
/* 計(jì)算分片個(gè)數(shù)。*/
if (fileSize % partSize != 0) {
partCount++;
}
/* 對(duì)每一個(gè)分片進(jìn)行上傳。*/
for (int i = 1; i <= partCount; i++) {
auto skipBytes = partSize * (i - 1);
auto size = (partSize < fileSize - skipBytes) ? partSize : (fileSize - skipBytes);
std::shared_ptr<std::iostream> content = std::make_shared<std::fstream>(fileToUpload, std::ios::in|std::ios::binary);
content->seekg(skipBytes, std::ios::beg);
UploadPartRequest uploadPartRequest(BucketName, ObjectName, content);
uploadPartRequest.setContentLength(size);
uploadPartRequest.setUploadId(uploadId);
uploadPartRequest.setPartNumber(i);
auto uploadPartOutcome = client.UploadPart(uploadPartRequest, cryptoCtx);
if (uploadPartOutcome.isSuccess()) {
Part part(i, uploadPartOutcome.result().ETag());
partETagList.push_back(part);
}
else {
std::cout << "uploadPart fail" <<
",code:" << uploadPartOutcome.error().Code() <<
",message:" << uploadPartOutcome.error().Message() <<
",requestId:" << uploadPartOutcome.error().RequestId() << std::endl;
}
}
/* 完成分片上傳。*/
CompleteMultipartUploadRequest request(BucketName, ObjectName);
request.setUploadId(uploadId);
request.setPartList(partETagList);
auto outcome = client.CompleteMultipartUpload(request, cryptoCtx);
if (!outcome.isSuccess()) {
/* 異常處理。*/
std::cout << "CompleteMultipartUpload fail" <<
",code:" << outcome.error().Code() <<
",message:" << outcome.error().Message() <<
",requestId:" << outcome.error().RequestId() << std::endl;
return -1;
}
/* 釋放網(wǎng)絡(luò)等資源。*/
ShutdownSdk();
return 0;
}
下載到本地文件
以下代碼用于使用主密鑰RSA解密下載到本地的文件:
#include <alibabacloud/oss/OssEncryptionClient.h>
#include <fstream>
using namespace AlibabaCloud::OSS;
int main(void)
{
/* 初始化OSS賬號(hào)信息。*/
/* yourEndpoint填寫B(tài)ucket所在地域?qū)?yīng)的Endpoint。以華東1(杭州)為例,Endpoint填寫為https://oss-cn-hangzhou.aliyuncs.com。*/
std::string Endpoint = "yourEndpoint";
/* yourRegion填寫B(tài)ucket所在地域?qū)?yīng)的Region。以華東1(杭州)為例,Region填寫為cn-hangzhou。*/
std::string Region = "yourRegion";
/* 填寫B(tài)ucket名稱,例如examplebucket。*/
std::string BucketName = "examplebucket";
/* 填寫Object完整路徑,完整路徑中不能包含Bucket名稱,例如exampledir/exampleobject.txt。*/
std::string ObjectName = "exampledir/exampleobject.txt";
/* 下載Object到本地文件examplefile.txt,并保存到指定的本地路徑中(D:\\localpath)。如果指定的本地文件存在會(huì)覆蓋,不存在則新建。*/
/* 如果未指定本地路徑,則下載后的文件默認(rèn)保存到示例程序所屬項(xiàng)目對(duì)應(yīng)本地路徑中。*/
std::string FileNametoSave = "D:\\localpath\\examplefile.txt";
/* 主密鑰及描述信息。*/
std::string RSAPublicKey = "your rsa public key";
std::string RSAPrivateKey = "your rsa private key";
std::map<std::string, std::string> desc;
desc["comment"] = "your comment";
/* 初始化網(wǎng)絡(luò)等資源。*/
InitializeSdk();
ClientConfiguration conf;
conf.signatureVersion = SignatureVersionType::V4;
/* 從環(huán)境變量中獲取訪問憑證。運(yùn)行本代碼示例之前,請(qǐng)確保已設(shè)置環(huán)境變量OSS_ACCESS_KEY_ID和OSS_ACCESS_KEY_SECRET。*/
auto credentialsProvider = std::make_shared<EnvironmentVariableCredentialsProvider>();
OssClient client(Endpoint, credentialsProvider, conf);
client.SetRegion(Region);
CryptoConfiguration cryptoConf;
auto materials = std::make_shared<SimpleRSAEncryptionMaterials>(RSAPublicKey, RSAPrivateKey, desc);
/* 如果需要解密不同主密鑰加密的內(nèi)容, 需要傳對(duì)應(yīng)的密鑰信息。*/
//std::string RSAPublicKey2 = "your rsa public key";
//std::string RSAPrivateKey2 = "your rsa private key";
//std::map<std::string, std::string> desc2;
//desc2["comment"] = "your comment";
//materials.addEncryptionMaterial(RSAPublicKey2, RSAPrivateKey2, desc2);
OssEncryptionClient client(Endpoint, credentialsProvider, conf, materials, cryptoConf);
/* 獲取文件到本地文件。*/
GetObjectRequest request(BucketName, ObjectName);
request.setResponseStreamFactory([=]() {return std::make_shared<std::fstream>(FileNametoSave, std::ios_base::out | std::ios_base::in | std::ios_base::trunc| std::ios_base::binary); });
auto outcome = client.GetObject(request);
if (outcome.isSuccess()) {
std::cout << "GetObjectToFile success" << outcome.result().Metadata().ContentLength() << std::endl;
}
else {
/* 異常處理。*/
std::cout << "GetObjectToFile fail" <<
",code:" << outcome.error().Code() <<
",message:" << outcome.error().Message() <<
",requestId:" << outcome.error().RequestId() << std::endl;
return -1;
}
/* 釋放網(wǎng)絡(luò)等資源。*/
ShutdownSdk();
return 0;
}
下載到本地內(nèi)存
以下代碼用于使用主密鑰RSA解密下載到本地內(nèi)存的文件:
#include <alibabacloud/oss/OssEncryptionClient.h>
using namespace AlibabaCloud::OSS;
int main(void)
{
/* 初始化OSS賬號(hào)信息。*/
/* yourEndpoint填寫B(tài)ucket所在地域?qū)?yīng)的Endpoint。以華東1(杭州)為例,Endpoint填寫為https://oss-cn-hangzhou.aliyuncs.com。*/
std::string Endpoint = "yourEndpoint";
/* yourRegion填寫B(tài)ucket所在地域?qū)?yīng)的Region。以華東1(杭州)為例,Region填寫為cn-hangzhou。*/
std::string Region = "yourRegion";
/* 填寫B(tài)ucket名稱,例如examplebucket。*/
std::string BucketName = "examplebucket";
/* 填寫不包含Bucket名稱在內(nèi)的Object的完整路徑,例如desrfolder/exampleobject.txt。*/
std::string ObjectName = "yourObjectName";
std::string RSAPublicKey = "your rsa public key";
std::string RSAPrivateKey = "your rsa private key";
/* 主密鑰及描述信息。*/
std::string RSAPublicKey = "your rsa public key";
std::string RSAPrivateKey = "your rsa private key";
std::map<std::string, std::string> desc;
desc["comment"] = "your comment";
/* 初始化網(wǎng)絡(luò)等資源。*/
InitializeSdk();
ClientConfiguration conf;
conf.signatureVersion = SignatureVersionType::V4;
/* 從環(huán)境變量中獲取訪問憑證。運(yùn)行本代碼示例之前,請(qǐng)確保已設(shè)置環(huán)境變量OSS_ACCESS_KEY_ID和OSS_ACCESS_KEY_SECRET。*/
auto credentialsProvider = std::make_shared<EnvironmentVariableCredentialsProvider>();
OssClient client(Endpoint, credentialsProvider, conf);
client.SetRegion(Region);
CryptoConfiguration cryptoConf;
auto materials = std::make_shared<SimpleRSAEncryptionMaterials>(RSAPublicKey, RSAPrivateKey, desc);
/* 如果需要解密不同主密鑰加密的內(nèi)容, 需要傳對(duì)應(yīng)的密鑰信息。*/
//std::string RSAPublicKey2 = "your rsa public key";
//std::string RSAPrivateKey2 = "your rsa private key";
//std::map<std::string, std::string> desc2;
//desc2["comment"] = "your comment";
//materials.addEncryptionMaterial(RSAPublicKey2, RSAPrivateKey2, desc2);
OssEncryptionClient client(Endpoint, credentialsProvider, conf, materials, cryptoConf);
/* 獲取文件到本地內(nèi)存。*/
GetObjectRequest request(BucketName, ObjectName);
auto outcome = client.GetObject(request);
if (outcome.isSuccess()) {
std::cout << "getObjectToBuffer" << " success, Content-Length:" << outcome.result().Metadata().ContentLength() << std::endl;
/* 打印下載內(nèi)容。*/
std::string content;
*(outcome.result().Content()) >> content;
std::cout << "getObjectToBuffer" << "content:" << content << std::endl;
}
else {
/* 異常處理。*/
std::cout << "getObjectToBuffer fail" <<
",code:" << outcome.error().Code() <<
",message:" << outcome.error().Message() <<
",requestId:" << outcome.error().RequestId() << std::endl;
return -1;
}
/*釋放網(wǎng)絡(luò)等資源。*/
ShutdownSdk();
return 0;
}
范圍下載
以下代碼用于使用主密鑰RSA解密范圍下載的文件:
#include <alibabacloud/oss/OssEncryptionClient.h>
using namespace AlibabaCloud::OSS;
int main(void)
{
/* 初始化OSS賬號(hào)信息。*/
/* yourEndpoint填寫B(tài)ucket所在地域?qū)?yīng)的Endpoint。以華東1(杭州)為例,Endpoint填寫為https://oss-cn-hangzhou.aliyuncs.com。*/
std::string Endpoint = "yourEndpoint";
/* yourRegion填寫B(tài)ucket所在地域?qū)?yīng)的Region。以華東1(杭州)為例,Region填寫為cn-hangzhou。*/
std::string Region = "yourRegion";
/* 填寫B(tài)ucket名稱,例如examplebucket。*/
std::string BucketName = "examplebucket";
/* 填寫不包含Bucket名稱在內(nèi)的Object的完整路徑,例如desrfolder/exampleobject.txt。*/
std::string ObjectName = "yourObjectName";
/* 主密鑰及描述信息。*/
std::string RSAPublicKey = "your rsa public key";
std::string RSAPrivateKey = "your rsa private key";
std::map<std::string, std::string> desc;
desc["comment"] = "your comment";
/* 初始化網(wǎng)絡(luò)等資源。*/
InitializeSdk();
ClientConfiguration conf;
conf.signatureVersion = SignatureVersionType::V4;
/* 從環(huán)境變量中獲取訪問憑證。運(yùn)行本代碼示例之前,請(qǐng)確保已設(shè)置環(huán)境變量OSS_ACCESS_KEY_ID和OSS_ACCESS_KEY_SECRET。*/
auto credentialsProvider = std::make_shared<EnvironmentVariableCredentialsProvider>();
OssClient client(Endpoint, credentialsProvider, conf);
client.SetRegion(Region);
CryptoConfiguration cryptoConf;
auto materials = std::make_shared<SimpleRSAEncryptionMaterials>(RSAPublicKey, RSAPrivateKey, desc);
/* 如果需要解密不同主密鑰加密的內(nèi)容, 需要傳對(duì)應(yīng)的密鑰信息。*/
//std::string RSAPublicKey2 = "your rsa public key";
//std::string RSAPrivateKey2 = "your rsa private key";
//std::map<std::string, std::string> desc2;
//desc2["comment"] = "your comment";
//materials.addEncryptionMaterial(RSAPublicKey2, RSAPrivateKey2, desc2);
OssEncryptionClient client(Endpoint, credentialsProvider, conf, materials, cryptoConf);
/* 設(shè)置下載范圍。*/
GetObjectRequest request(BucketName, ObjectName);
request.setRange(0, 1);
auto outcome = client.GetObject(request);
if (!outcome.isSuccess ()) {
/* 異常處理。*/
std::cout << "getObject fail" <<
",code:" << outcome.error().Code() <<
",message:" << outcome.error().Message() <<
",requestId:" << outcome.error().RequestId() << std::endl;
return -1;
}
/* 釋放網(wǎng)絡(luò)等資源。*/
ShutdownSdk();
return 0;
}
斷點(diǎn)續(xù)傳下載
以下代碼用于使用主密鑰RSA解密斷點(diǎn)續(xù)傳下載的文件:
#include <alibabacloud/oss/OssEncryptionClient.h>
using namespace AlibabaCloud::OSS;
int main(void)
{
/* 初始化OSS賬號(hào)信息 */
/* yourEndpoint填寫B(tài)ucket所在地域?qū)?yīng)的Endpoint。以華東1(杭州)為例,Endpoint填寫為https://oss-cn-hangzhou.aliyuncs.com。*/
std::string Endpoint = "yourEndpoint";
/* yourRegion填寫B(tài)ucket所在地域?qū)?yīng)的Region。以華東1(杭州)為例,Region填寫為cn-hangzhou。*/
std::string Region = "yourRegion";
/* 填寫B(tài)ucket名稱,例如examplebucket。*/
std::string BucketName = "examplebucket";
/* 填寫Object完整路徑,完整路徑中不能包含Bucket名稱,例如exampledir/exampleobject.txt。*/
std::string ObjectName = "exampledir/exampleobject.txt";
/* 下載Object到本地文件examplefile.txt,并保存到指定的本地路徑中(D:\\localpath)。如果指定的本地文件存在會(huì)覆蓋,不存在則新建。*/
/* 如果未指定本地路徑,則下載后的文件默認(rèn)保存到示例程序所屬項(xiàng)目對(duì)應(yīng)本地路徑中。*/
std::string DownloadFilePath = "D:\\localpath\\examplefile.txt";
/* 設(shè)置斷點(diǎn)記錄文件的完整路徑,例如D:\\localpath\\examplefile.txt.dcp。*/
/* 只有當(dāng)Object下載中斷產(chǎn)生了斷點(diǎn)記錄文件后,如果需要繼續(xù)下載該Object,才需要設(shè)置對(duì)應(yīng)的斷點(diǎn)記錄文件。下載完成后,該文件會(huì)被刪除。*/
std::string CheckpointFilePath = "D:\\localpath\\examplefile.txt.dcp";
/* 主密鑰及描述信息。*/
std::string RSAPublicKey = "your rsa public key";
std::string RSAPrivateKey = "your rsa private key";
std::map<std::string, std::string> desc;
desc["comment"] = "your comment";
/* 初始化網(wǎng)絡(luò)等資源。*/
InitializeSdk();
ClientConfiguration conf;
conf.signatureVersion = SignatureVersionType::V4;
/* 從環(huán)境變量中獲取訪問憑證。運(yùn)行本代碼示例之前,請(qǐng)確保已設(shè)置環(huán)境變量OSS_ACCESS_KEY_ID和OSS_ACCESS_KEY_SECRET。*/
auto credentialsProvider = std::make_shared<EnvironmentVariableCredentialsProvider>();
OssClient client(Endpoint, credentialsProvider, conf);
client.SetRegion(Region);
CryptoConfiguration cryptoConf;
auto materials = std::make_shared<SimpleRSAEncryptionMaterials>(RSAPublicKey, RSAPrivateKey, desc);
/* 如果需要解密不同主密鑰加密的內(nèi)容, 需要傳對(duì)應(yīng)的密鑰信息。*/
//std::string RSAPublicKey2 = "your rsa public key";
//std::string RSAPrivateKey2 = "your rsa private key";
//std::map<std::string, std::string> desc2;
//desc2["comment"] = "your comment";
//materials.addEncryptionMaterial(RSAPublicKey2, RSAPrivateKey2, desc2);
OssEncryptionClient client(Endpoint, credentialsProvider, conf, materials, cryptoConf);
/* 斷點(diǎn)續(xù)傳下載。*/
DownloadObjectRequest request(BucketName, ObjectName, DownloadFilePath, CheckpointFilePath);
auto outcome = client.ResumableDownloadObject(request);
if (!outcome.isSuccess()) {
/* 異常處理。*/
std::cout << "ResumableDownloadObject fail" <<
",code:" << outcome.error().Code() <<
",message:" << outcome.error().Message() <<
",requestId:" << outcome.error().RequestId() << std::endl;
return -1;
}
/* 釋放網(wǎng)絡(luò)等資源。*/
ShutdownSdk();
return 0;
}