このトピックでは、同じリージョン内のバケット内またはバケット間でオブジェクトをコピーする方法について説明します。
使用上の注意
このトピックでは、中国 (杭州) リージョンのパブリックエンドポイントを使用しています。 OSS と同じリージョン内の他の Alibaba Cloud サービスから OSS にアクセスする場合は、内部エンドポイントを使用します。 OSS のリージョンとエンドポイントの詳細については、「リージョンとエンドポイント」をご参照ください。
このトピックでは、OSS エンドポイントを使用して OSSClient インスタンスを作成します。 カスタムドメイン名または Security Token Service (STS) を使用して OSSClient インスタンスを作成する場合は、「初期化」をご参照ください。
オブジェクトサイズに基づいて、CopyObject または UploadPartCopy 操作を呼び出してオブジェクトをコピーできます。 オブジェクトサイズの制限の詳細については、「CopyObject」をご参照ください。
小さいオブジェクトのアップロード
オブジェクトをコピーするには、ソースオブジェクトに対する読み取り権限と、デスティネーションバケットに対する読み取りおよび書き込み権限が必要です。
ソースバケットとデスティネーションバケットは、同じリージョンにある必要があります。 たとえば、中国 (杭州) リージョンにあるバケットから中国 (青島) リージョンにある別のバケットにオブジェクトをコピーすることはできません。
次のコードは、CopyObject 操作を呼び出して小さいオブジェクトをコピーする例を示しています。
#include "oss_api.h"
#include "aos_http_io.h"
/* Specify the endpoint of the region in which the bucket is located. For example, if the bucket is located in the China (Hangzhou) region, set the endpoint to https://oss-cn-hangzhou.aliyuncs.com. */
/* バケットが配置されているリージョンのエンドポイントを指定します。たとえば、バケットが中国 (杭州) リージョンにある場合は、エンドポイントを https://oss-cn-hangzhou.aliyuncs.com に設定します。 */
const char *endpoint = "yourEndpoint";
/* Specify the name of the source bucket. */
/* ソースバケットの名前を指定します。 */
const char *source_bucket_name = "yourSourceBucketName";
/* Specify the full path of the source object. Do not include the bucket name in the full path. */
/* ソースオブジェクトの完全なパスを指定します。完全なパスにバケット名を含めないでください。 */
const char *source_object_name = "yourSourceObjectName";
/* Specify the name of the destination bucket. The destination bucket must be in the same region as the source bucket. */
/* デスティネーションバケットの名前を指定します。デスティネーションバケットは、ソースバケットと同じリージョンにある必要があります。 */
const char *dest_bucket_name = "yourDestBucketName";
/* Specify the full path of the destination object. Do not include the bucket name in the full path. */
/* デスティネーションオブジェクトの完全なパスを指定します。完全なパスにバケット名を含めないでください。 */
const char *dest_object_name = "yourDestObjectName";
/* Specify the region in which the bucket is located. For example, if the bucket is located in the China (Hangzhou) region, set the region to cn-hangzhou. */
/* バケットが配置されているリージョンを指定します。たとえば、バケットが中国 (杭州) リージョンにある場合は、リージョンを cn-hangzhou に設定します。 */
const char *region = "yourRegion";
void init_options(oss_request_options_t *options)
{
options->config = oss_config_create(options->pool);
/* Use a char* string to initialize data of the aos_string_t type. */
/* char* 文字列を使用して aos_string_t 型のデータを初期化します。 */
aos_str_set(&options->config->endpoint, endpoint);
/* Obtain access credentials from environment variables. Before you run the sample code, make sure that the OSS_ACCESS_KEY_ID and OSS_ACCESS_KEY_SECRET environment variables are configured. */
/* 環境変数からアクセス認証情報を取得します。サンプルコードを実行する前に、OSS_ACCESS_KEY_ID および OSS_ACCESS_KEY_SECRET 環境変数が構成されていることを確認してください。 */
aos_str_set(&options->config->access_key_id, getenv("OSS_ACCESS_KEY_ID"));
aos_str_set(&options->config->access_key_secret, getenv("OSS_ACCESS_KEY_SECRET"));
// Specify two additional parameters.
// 2 つの追加パラメーターを指定します。
aos_str_set(&options->config->region, region);
options->config->signature_version = 4;
/* Specify whether to use CNAME. The value 0 indicates that CNAME is not used. */
/* CNAME を使用するかどうかを指定します。値 0 は、CNAME が使用されていないことを示します。 */
options->config->is_cname = 0;
/* Specify network parameters, such as the timeout period. */
/* タイムアウト期間などのネットワークパラメーターを指定します。 */
options->ctl = aos_http_controller_create(options->pool, 0);
}
int main(int argc, char *argv[])
{
/* Call the aos_http_io_initialize method in main() to initialize global resources, such as network resources and memory resources. */
/* main() で aos_http_io_initialize メソッドを呼び出して、ネットワークリソースやメモリリソースなどのグローバルリソースを初期化します。 */
if (aos_http_io_initialize(NULL, 0) != AOSE_OK) {
exit(1);
}
/* Create a memory pool to manage memory. aos_pool_t is equivalent to apr_pool_t. The code used to create a memory pool is included in the APR library. */
/* メモリを管理するためのメモリプールを作成します。 aos_pool_t は apr_pool_t と同等です。メモリプールを作成するために使用されるコードは、APR ライブラリに含まれています。 */
aos_pool_t *pool;
/* Create a memory pool. The value of the second parameter is NULL. This value indicates that the pool does not inherit other memory pools. */
/* メモリプールを作成します。2 番目のパラメーターの値は NULL です。この値は、プールが他のメモリプールを継承しないことを示します。 */
aos_pool_create(&pool, NULL);
/* Create and initialize options. This parameter includes global configuration information, such as endpoint, access_key_id, access_key_secret, is_cname, and curl. */
/* オプションを作成して初期化します。このパラメーターには、エンドポイント、access_key_id、access_key_secret、is_cname、curl などのグローバル構成情報が含まれています。 */
oss_request_options_t *oss_client_options;
/* Allocate the memory resources in the memory pool to the options. */
/* メモリプール内のメモリリソースをオプションに割り当てます。 */
oss_client_options = oss_request_options_create(pool);
/* Initialize oss_client_options. */
/* oss_client_options を初期化します。 */
init_options(oss_client_options);
/* Initialize the parameters. */
/* パラメーターを初期化します。 */
aos_string_t source_bucket;
aos_string_t source_object;
aos_string_t dest_bucket;
aos_string_t dest_object;
aos_table_t *headers = NULL;
aos_table_t *resp_headers = NULL;
aos_status_t *resp_status = NULL;
aos_str_set(&source_bucket, source_bucket_name);
aos_str_set(&source_object, source_object_name);
aos_str_set(&dest_bucket, dest_bucket_name);
aos_str_set(&dest_object, dest_object_name);
headers = aos_table_make(pool, 0);
/* Copy the object. */
/* オブジェクトをコピーします。 */
resp_status = oss_copy_object(oss_client_options, &source_bucket, &source_object, &dest_bucket, &dest_object, headers, &resp_headers);
if (aos_status_is_ok(resp_status)) {
printf("copy object succeeded\n"); // オブジェクトのコピーに成功しました
} else {
printf("copy object failed\n"); // オブジェクトのコピーに失敗しました
}
/* Release the memory pool. This operation releases the memory resources allocated for the request. */
/* メモリプールを解放します。この操作は、リクエストに割り当てられたメモリリソースを解放します。 */
aos_pool_destroy(pool);
/* Release the allocated global resources. */
/* 割り当てられたグローバルリソースを解放します。 */
aos_http_io_deinitialize();
return 0;
}大きいオブジェクトのコピー
次のコードは、UploadPartCopy 操作を呼び出してマルチパートコピーを実行する例を示しています。
#include "oss_api.h"
#include "aos_http_io.h"
#include <sys/stat.h>
/* Specify the endpoint of the region in which the bucket is located. For example, if the bucket is located in the China (Hangzhou) region, set the endpoint to https://oss-cn-hangzhou.aliyuncs.com. */
/* バケットが配置されているリージョンのエンドポイントを指定します。たとえば、バケットが中国 (杭州) リージョンにある場合は、エンドポイントを https://oss-cn-hangzhou.aliyuncs.com に設定します。 */
const char *endpoint = "yourEndpoint";
/* Specify the name of the source bucket. */
/* ソースバケットの名前を指定します。 */
const char *source_bucket_name = "yourSourceBucketName";
/* Specify the full path of the source object. Do not include the bucket name in the full path. */
/* ソースオブジェクトの完全なパスを指定します。完全なパスにバケット名を含めないでください。 */
const char *source_object_name = "yourSourceObjectName";
/* Specify the name of the destination bucket. The destination bucket must be in the same region as the source bucket. */
/* デスティネーションバケットの名前を指定します。デスティネーションバケットは、ソースバケットと同じリージョンにある必要があります。 */
const char *dest_bucket_name = "yourDestBucketName";
/* Specify the full path of the destination object. Do not include the bucket name in the full path. */
/* デスティネーションオブジェクトの完全なパスを指定します。完全なパスにバケット名を含めないでください。 */
const char *dest_object_name = "yourDestObjectName";
/* Specify the region in which the bucket is located. For example, if the bucket is located in the China (Hangzhou) region, set the region to cn-hangzhou. */
/* バケットが配置されているリージョンを指定します。たとえば、バケットが中国 (杭州) リージョンにある場合は、リージョンを cn-hangzhou に設定します。 */
const char *region = "yourRegion";
void init_options(oss_request_options_t* options)
{
options->config = oss_config_create(options->pool);
/* Use a char* string to initialize data of the aos_string_t type. */
/* char* 文字列を使用して aos_string_t 型のデータを初期化します。 */
aos_str_set(&options->config->endpoint, endpoint);
/* Obtain access credentials from environment variables. Before you run the sample code, make sure that the OSS_ACCESS_KEY_ID and OSS_ACCESS_KEY_SECRET environment variables are configured. */
/* 環境変数からアクセス認証情報を取得します。サンプルコードを実行する前に、OSS_ACCESS_KEY_ID および OSS_ACCESS_KEY_SECRET 環境変数が構成されていることを確認してください。 */
aos_str_set(&options->config->access_key_id, getenv("OSS_ACCESS_KEY_ID"));
aos_str_set(&options->config->access_key_secret, getenv("OSS_ACCESS_KEY_SECRET"));
// Specify two additional parameters.
// 2 つの追加パラメーターを指定します。
aos_str_set(&options->config->region, region);
options->config->signature_version = 4;
/* Specify whether to use CNAME. The value 0 indicates that CNAME is not used. */
/* CNAME を使用するかどうかを指定します。値 0 は、CNAME が使用されていないことを示します。 */
options->config->is_cname = 0;
/* Specify network parameters, such as the timeout period. */
/* タイムアウト期間などのネットワークパラメーターを指定します。 */
options->ctl = aos_http_controller_create(options->pool, 0);
}
int main(int argc, char* argv[])
{
/* Call the aos_http_io_initialize method in main() to initialize global resources, such as network resources and memory resources. */
/* main() で aos_http_io_initialize メソッドを呼び出して、ネットワークリソースやメモリリソースなどのグローバルリソースを初期化します。 */
if (aos_http_io_initialize(NULL, 0) != AOSE_OK) {
exit(1);
}
/* Create a memory pool to manage memory. aos_pool_t is equivalent to apr_pool_t. The code used to create a memory pool is included in the APR library. */
/* メモリを管理するためのメモリプールを作成します。 aos_pool_t は apr_pool_t と同等です。メモリプールを作成するために使用されるコードは APR ライブラリに含まれています。 */
aos_pool_t* pool;
/* Create a memory pool. The value of the second parameter is NULL. This value indicates that the pool does not inherit other memory pools. */
/* メモリプールを作成します。 2 番目のパラメーターの値は NULL です。 この値は、プールが他のメモリプールを継承しないことを示します。 */
aos_pool_create(&pool, NULL);
/* Create and initialize options. This parameter includes global configuration information, such as endpoint, access_key_id, access_key_secret, is_cname, and curl. */
/* オプションを作成して初期化します。 このパラメーターには、エンドポイント、access_key_id、access_key_secret、is_cname、curl などのグローバル構成情報が含まれています。 */
oss_request_options_t* oss_client_options;
/* Allocate the memory resources in the memory pool to the options. */
/* メモリプール内のメモリリソースをオプションに割り当てます。 */
oss_client_options = oss_request_options_create(pool);
/* Initialize oss_client_options. */
/* oss_client_options を初期化します。 */
init_options(oss_client_options);
/* Initialize the parameters. */
/* パラメーターを初期化します。 */
aos_string_t src_bucket;
aos_string_t src_object;
aos_string_t dest_bucket;
aos_string_t dest_object;
aos_string_t upload_id;
aos_table_t* headers = NULL;
aos_table_t* resp_headers = NULL;
aos_status_t* resp_status = NULL;
oss_list_upload_part_params_t* list_upload_part_params;
oss_upload_part_copy_params_t* upload_part_copy_params1;
oss_upload_part_copy_params_t* upload_part_copy_params2;
oss_list_part_content_t* part_content;
aos_list_t complete_part_list;
oss_complete_part_content_t* complete_content;
aos_table_t* list_part_resp_headers = NULL;
aos_table_t* complete_resp_headers = NULL;
int part1 = 1;
int part2 = 2;
int64_t range_start1 = 0;
int64_t range_end1 = 6000000;//not less than 5MB // 5MB 以上
int64_t range_start2 = 6000001;
int64_t range_end2;
int max_ret = 1000;
int64_t content_length = 0;
/* Obtain the size of the source object. */
/* ソースオブジェクトのサイズを取得します。 */
headers = aos_table_make(pool, 0);
aos_str_set(&src_bucket, source_bucket_name);
aos_str_set(&src_object, source_object_name);
resp_status = oss_head_object(oss_client_options, &src_bucket, &src_object, headers, &resp_headers);
if (aos_status_is_ok(resp_status)) {
char *content_length_str = (char*)apr_table_get(resp_headers, OSS_CONTENT_LENGTH);
if (content_length_str != NULL) {
content_length = atoll(content_length_str);
}
printf("head object succeeded\n"); // head オブジェクトが成功しました
}
else {
printf("head object failed\n"); // head オブジェクトが失敗しました
}
/* Initiate a multipart copy task. */
/* マルチパートコピータスクを開始します。 */
headers = aos_table_make(pool, 0);
aos_str_set(&dest_bucket, dest_bucket_name);
aos_str_set(&dest_object, dest_object_name);
resp_status = oss_init_multipart_upload(oss_client_options, &dest_bucket, &dest_object, &upload_id, headers, &resp_headers);
if (aos_status_is_ok(resp_status)) {
printf("init multipart upload succeeded, upload_id is %s\n", upload_id.data); // マルチパートアップロードの初期化に成功しました。 upload_id は %s です
}
else {
printf("init multipart upload failed\n"); // マルチパートアップロードの初期化に失敗しました
}
/* Copy the first part. */
/* 最初の部分をコピーします。 */
upload_part_copy_params1 = oss_create_upload_part_copy_params(pool);
aos_str_set(&upload_part_copy_params1->source_bucket, source_bucket_name);
aos_str_set(&upload_part_copy_params1->source_object, source_object_name);
aos_str_set(&upload_part_copy_params1->dest_bucket, dest_bucket_name);
aos_str_set(&upload_part_copy_params1->dest_object, dest_object_name);
aos_str_set(&upload_part_copy_params1->upload_id, upload_id.data);
upload_part_copy_params1->part_num = part1;
upload_part_copy_params1->range_start = range_start1;
upload_part_copy_params1->range_end = range_end1;
headers = aos_table_make(pool, 0);
resp_status = oss_upload_part_copy(oss_client_options, upload_part_copy_params1, headers, &resp_headers);
if (aos_status_is_ok(resp_status)) {
printf("upload part 1 copy succeeded\n"); // パート 1 のコピーのアップロードに成功しました
}
else {
printf("upload part 1 copy failed\n"); // パート 1 のコピーのアップロードに失敗しました
}
/* Copy the second part. */
/* 2 番目の部分をコピーします。 */
range_end2 = content_length - 1;
upload_part_copy_params2 = oss_create_upload_part_copy_params(pool);
aos_str_set(&upload_part_copy_params2->source_bucket, source_bucket_name);
aos_str_set(&upload_part_copy_params2->source_object, source_object_name);
aos_str_set(&upload_part_copy_params2->dest_bucket, dest_bucket_name);
aos_str_set(&upload_part_copy_params2->dest_object, dest_object_name);
aos_str_set(&upload_part_copy_params2->upload_id, upload_id.data);
upload_part_copy_params2->part_num = part2;
upload_part_copy_params2->range_start = range_start2;
upload_part_copy_params2->range_end = range_end2;
headers = aos_table_make(pool, 0);
resp_status = oss_upload_part_copy(oss_client_options, upload_part_copy_params2, headers, &resp_headers);
if (aos_status_is_ok(resp_status)) {
printf("upload part 2 copy succeeded\n"); // パート 2 のコピーのアップロードに成功しました
}
else {
printf("upload part 2 copy failed\n"); // パート 2 のコピーのアップロードに失敗しました
}
/* List the copied parts. */
/* コピーされたパートをリストします。 */
headers = aos_table_make(pool, 0);
list_upload_part_params = oss_create_list_upload_part_params(pool);
list_upload_part_params->max_ret = max_ret;
aos_list_init(&complete_part_list);
resp_status = oss_list_upload_part(oss_client_options, &dest_bucket, &dest_object, &upload_id, list_upload_part_params, &list_part_resp_headers);
aos_list_for_each_entry(oss_list_part_content_t, part_content, &list_upload_part_params->part_list, node) {
complete_content = oss_create_complete_part_content(pool);
aos_str_set(&complete_content->part_number, part_content->part_number.data);
aos_str_set(&complete_content->etag, part_content->etag.data);
aos_list_add_tail(&complete_content->node, &complete_part_list);
}
/* Complete the multipart copy task. */
/* マルチパートコピータスクを完了します。 */
resp_status = oss_complete_multipart_upload(oss_client_options, &dest_bucket, &dest_object, &upload_id, &complete_part_list, headers, &complete_resp_headers);
if (aos_status_is_ok(resp_status)) {
printf("complete multipart upload succeeded\n"); // マルチパートアップロードの完了に成功しました
}
else {
printf("complete multipart upload failed\n"); // マルチパートアップロードの完了に失敗しました
}
/* Release the memory pool. This operation releases the memory resources allocated for the request. */
/* メモリプールを解放します。 この操作は、リクエストに割り当てられたメモリリソースを解放します。 */
aos_pool_destroy(pool);
/* Release the allocated global resources. */
/* 割り当てられたグローバルリソースを解放します。 */
aos_http_io_deinitialize();
return 0;
}関連情報
小さいオブジェクトのコピー
小さいオブジェクトのコピーに呼び出すことができる API 操作の詳細については、「CopyObject」をご参照ください。
大きいオブジェクトのコピー
大きいオブジェクトのコピーに呼び出すことができる API 操作の詳細については、「UploadPartCopy」をご参照ください。