

本文為英文版的機器翻譯版本，如內容有任何歧義或不一致之處，概以英文版為準。

# 使用 的 Amazon S3 程式碼範例 適用於 C\$1\$1 的 AWS SDK
<a name="examples-s3"></a>

[Amazon S3](https://aws.amazon.com/s3) 是物件儲存體，用於從任何地方存放和擷取任意數量的資料。提供多個類別 適用於 C\$1\$1 的 AWS SDK 以與 Amazon S3 連接。

**注意**  
本指南僅提供示範特定技術所需的程式碼，但[完整的範例程式碼可在 GitHub 上取得](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp)。在 GitHub 上，您可以下載單一來源檔案，也可以在本機複製儲存庫，以取得、建置和執行所有範例。
+ [https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-s3/html/class_aws_1_1_s3_1_1_s3_client.html](https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-s3/html/class_aws_1_1_s3_1_1_s3_client.html) 類別 

  `S3Client` 程式庫是功能完整的 Amazon S3 介面。

  此集中`list_buckets_disabling_dns_cache.cpp`的範例專為在 Linux/Mac 上使用 CURL 而設計 （雖然可以修改為在 Windows 上使用）。如果您在 Windows 上，請在建置專案`list_buckets_disabling_dns_cache.cpp`之前刪除 檔案，因為它依賴 Linux 的 curl HttpClient。

  使用 的範例程式碼`S3Client`位於 Github 的 [`s3` 資料夾中](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp/example_code/s3)。如需此範例集示範的完整函數清單，請參閱 Github 上的[讀我](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp/example_code/s3/README.md)檔案。

  本指南中會詳細說明`s3`範例集的部分：
  + [建立、列出和刪除儲存貯體](examples-s3-buckets.md)
  + [可對物件執行的操作](examples-s3-objects.md) – 上傳和下載資料物件
  + [管理 Amazon S3 存取許可](examples-s3-access-permissions.md)
  + [使用儲存貯體政策管理對 Amazon S3 儲存貯體的存取](examples-s3-bucket-policies.md)
  + [將 Amazon S3 儲存貯體設定為網站](examples-s3-website-configuration.md)
+ [https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-s3-crt/html/class_aws_1_1_s3_crt_1_1_s3_crt_client.html](https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-s3-crt/html/class_aws_1_1_s3_crt_1_1_s3_crt_client.html) 類別 

  `S3CrtClient` 已在 SDK 的 1.9 版中新增 。 為 Amazon S3 GET （下載） 和 PUT （上傳） 操作`S3CrtClient`提供高輸送量。在 AWS 通用執行期 (CRT) 程式庫的頂端`S3CrtClient`實作 。

  使用 的範例程式碼`S3CrtClient`位於 Github 的 [`s3-crt` 資料夾中](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp/example_code/s3-crt)。如需此範例集示範的完整函數清單，請參閱 Github 上的[讀我](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp/example_code/s3-crt/README.md)檔案。
  + [使用 `S3CrtClient`進行 Amazon S3 操作](examples-s3-crt.md)
+ [https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-transfer/html/class_aws_1_1_transfer_1_1_transfer_manager.html](https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-transfer/html/class_aws_1_1_transfer_1_1_transfer_manager.html) 類別 

  `TransferManager` 是一種全受管服務，可透過檔案傳輸協定 (FTP)、透過 SSL 的檔案傳輸協定 (FTPS) 或 Secure Shell (SSH) 檔案傳輸協定 (SFTP) 直接傳入和傳出 Amazon S3。

  使用 的範例程式碼`TransferManager`位於 Github 的 [`transfer-manager` 資料夾中](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp/example_code/transfer-manager)。如需此範例集示範的完整函數清單，請參閱 Github 上的[讀我](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp/example_code/transfer-manager/README.md)檔案。
  + [將 TransferManager 用於 Amazon S3 操作](examples-s3-transfermanager.md)

# 建立、列出和刪除儲存貯體
<a name="examples-s3-buckets"></a>

Amazon Simple Storage Service (Amazon S3) 中的每個*物件*或檔案都包含在代表物件資料夾的*儲存貯*體中。每個儲存貯體都有一個全域唯一的名稱 AWS。如需詳細資訊，請參閱《[Amazon Simple Storage Service 使用者指南》中的使用 Amazon S3 儲存貯](https://docs.aws.amazon.com/AmazonS3/latest/dev/UsingBucket.html)體。

## 先決條件
<a name="codeExamplePrereq"></a>

開始之前，建議您先閱讀[開始使用 適用於 C\$1\$1 的 AWS SDK](getting-started.md)。

下載範例程式碼並建置解決方案，如 中所述[程式碼範例入門](getting-started-code-examples.md)。

若要執行範例，您的程式碼用來發出請求的使用者設定檔必須具有 AWS （針對 服務和 動作） 的適當許可。如需詳細資訊，請參閱[提供 AWS 登入](credentials.md)資料。

## 列出儲存貯體
<a name="list-buckets"></a>

若要執行`list_buckets`範例，請在命令提示字元中，導覽至建置系統建立建置可執行檔的資料夾。像 一樣執行可執行檔 `run_list_buckets`（您的完整可執行檔名會根據您的作業系統而有所不同）。如果您有任何儲存貯體，輸出會列出您帳戶的儲存貯體，或者如果您沒有任何儲存貯體，則會顯示空白清單。

在 中`list_buckets.cpp`，有兩種方法。
+ `main()` 呼叫 `ListBuckets()`。
+ `ListBuckets()` 使用 SDK 查詢您的儲存貯體。

`S3Client` 物件會呼叫 SDK 的 `ListBuckets()`方法。如果成功， 方法會傳回包含`ListBucketOutcome`物件的`ListBucketResult`物件。`ListBucketResult` 物件會呼叫 `GetBuckets()`方法，以取得包含您帳戶中每個 Amazon S3 儲存貯體相關資訊的`Bucket`物件清單。

 **Code** 

```
bool AwsDoc::S3::listBuckets(const Aws::S3::S3ClientConfiguration &clientConfig) {
    Aws::S3::S3Client client(clientConfig);

    auto outcome = client.ListBuckets();

    bool result = true;
    if (!outcome.IsSuccess()) {
        std::cerr << "Failed with error: " << outcome.GetError() << std::endl;
        result = false;
    } else {
        std::cout << "Found " << outcome.GetResult().GetBuckets().size() << " buckets\n";
        for (auto &&b: outcome.GetResult().GetBuckets()) {
            std::cout << b.GetName() << std::endl;
        }
    }

    return result;
}
```

請參閱 Github 上的完整 [list\$1buckets 範例](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp/example_code/s3/list_buckets.cpp)。

## 建立 儲存貯體
<a name="create-bucket"></a>



若要執行`create_bucket`範例，請在命令提示字元中，導覽至建置系統建立建置可執行檔的資料夾。像 一樣執行可執行檔 `run_create_bucket`（您的完整可執行檔名會根據您的作業系統而有所不同）。程式碼會在您的帳戶下建立空儲存貯體，然後顯示請求的成功或失敗。

在 中`create_bucket.cpp`，有兩種方法。
+ `main()` 呼叫 `CreateBucket()`。在 中`main()`，您需要使用 將 AWS 區域 變更為帳戶的 區域`enum`。您可以登入 並找到右上角的區域[AWS 管理主控台](https://console.aws.amazon.com/)，以檢視您 帳戶的 區域。
+ `CreateBucket()` 使用 SDK 來建立儲存貯體。



`S3Client` 物件會呼叫 SDK 的 `CreateBucket()`方法，`CreateBucketRequest`以儲存貯體的名稱傳入 。根據預設，儲存貯體會在 *us-east-1* （維吉尼亞北部） 區域中建立。如果您的區域不是 *us-east-1*，則程式碼會設定儲存貯體限制，以確保儲存貯體在您的區域中建立。

 **Code** 

```
bool AwsDoc::S3::createBucket(const Aws::String &bucketName,
                              const Aws::S3::S3ClientConfiguration &clientConfig) {
    Aws::S3::S3Client client(clientConfig);
    Aws::S3::Model::CreateBucketRequest request;
    request.SetBucket(bucketName);

    if (clientConfig.region != "us-east-1") {
        Aws::S3::Model::CreateBucketConfiguration createBucketConfig;
        createBucketConfig.SetLocationConstraint(
                Aws::S3::Model::BucketLocationConstraintMapper::GetBucketLocationConstraintForName(
                        clientConfig.region));
        request.SetCreateBucketConfiguration(createBucketConfig);
    }

    Aws::S3::Model::CreateBucketOutcome outcome = client.CreateBucket(request);
    if (!outcome.IsSuccess()) {
        auto err = outcome.GetError();
        std::cerr << "Error: createBucket: " <<
                  err.GetExceptionName() << ": " << err.GetMessage() << std::endl;
    } else {
        std::cout << "Created bucket " << bucketName <<
                  " in the specified AWS Region." << std::endl;
    }

    return outcome.IsSuccess();
}
```

請參閱 Github 上完整的 [create\$1buckets 範例](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp/example_code/s3/create_bucket.cpp)。

## 刪除 儲存貯體
<a name="delete-bucket"></a>



若要執行`delete_bucket`範例，請在命令提示字元中，導覽至建置系統建立建置可執行檔的資料夾。像 一樣執行可執行檔 `run_delete_bucket`（您的完整可執行檔名會根據您的作業系統而有所不同）。程式碼會刪除您帳戶中指定的儲存貯體，然後顯示請求的成功或失敗。

在 `delete_bucket.cpp`中有兩種方法。
+ `main()` 呼叫 `DeleteBucket()`。在 中`main()`，您需要使用 將 AWS 區域 變更為帳戶的 區域`enum`。您也需要將 `bucket_name` 變更為要刪除的儲存貯體名稱。
+ `DeleteBucket()` 使用 SDK 刪除儲存貯體。



`S3Client` 物件使用 SDK 的 `DeleteBucket()`方法，傳入具有要刪除之儲存貯體名稱的`DeleteBucketRequest`物件。儲存貯體必須為空，才能成功。

 **Code**

```
bool AwsDoc::S3::deleteBucket(const Aws::String &bucketName,
                              const Aws::S3::S3ClientConfiguration &clientConfig) {

    Aws::S3::S3Client client(clientConfig);

    Aws::S3::Model::DeleteBucketRequest request;
    request.SetBucket(bucketName);

    Aws::S3::Model::DeleteBucketOutcome outcome =
            client.DeleteBucket(request);

    if (!outcome.IsSuccess()) {
        const Aws::S3::S3Error &err = outcome.GetError();
        std::cerr << "Error: deleteBucket: " <<
                  err.GetExceptionName() << ": " << err.GetMessage() << std::endl;
    } else {
        std::cout << "The bucket was deleted" << std::endl;
    }

    return outcome.IsSuccess();
}
```

請參閱 Github 上完整的 [delete\$1bucket 範例](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp/example_code/s3/delete_bucket.cpp)。

# 可對物件執行的操作
<a name="examples-s3-objects"></a>

Amazon S3 物件代表*檔案*，這是資料集合。每個物件都必須位於儲存[貯](examples-s3-buckets.md)體中。

## 先決條件
<a name="codeExamplePrereq"></a>

開始之前，建議您先閱讀[開始使用 適用於 C\$1\$1 的 AWS SDK](getting-started.md)。

下載範例程式碼並建置解決方案，如中所述[程式碼範例入門](getting-started-code-examples.md)。

若要執行範例，您的程式碼用來提出請求的使用者描述檔必須具有 AWS （針對 服務和 動作） 的適當許可。如需詳細資訊，請參閱[提供 AWS 登入](credentials.md)資料。

## 將檔案上傳至儲存貯體
<a name="upload-object"></a>

使用 `S3Client` 物件`PutObject`函數，提供儲存貯體名稱、金鑰名稱和要上傳的檔案。 `Aws::FStream` 用於將本機檔案的內容上傳至儲存貯體。儲存貯體必須存在，否則會產生錯誤。

如需非同步上傳物件的範例，請參閱 [使用 進行非同步程式設計 適用於 C\$1\$1 的 AWS SDK](async-methods.md)

 **Code** 

```
bool AwsDoc::S3::putObject(const Aws::String &bucketName,
                           const Aws::String &fileName,
                           const Aws::S3::S3ClientConfiguration &clientConfig) {
    Aws::S3::S3Client s3Client(clientConfig);

    Aws::S3::Model::PutObjectRequest request;
    request.SetBucket(bucketName);
    //We are using the name of the file as the key for the object in the bucket.
    //However, this is just a string and can be set according to your retrieval needs.
    request.SetKey(fileName);

    std::shared_ptr<Aws::IOStream> inputData =
            Aws::MakeShared<Aws::FStream>("SampleAllocationTag",
                                          fileName.c_str(),
                                          std::ios_base::in | std::ios_base::binary);

    if (!*inputData) {
        std::cerr << "Error unable to read file " << fileName << std::endl;
        return false;
    }

    request.SetBody(inputData);

    Aws::S3::Model::PutObjectOutcome outcome =
            s3Client.PutObject(request);

    if (!outcome.IsSuccess()) {
        std::cerr << "Error: putObject: " <<
                  outcome.GetError().GetMessage() << std::endl;
    } else {
        std::cout << "Added object '" << fileName << "' to bucket '"
                  << bucketName << "'.";
    }

    return outcome.IsSuccess();
}
```

請參閱 GitHub 上的[完整範例](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp/example_code/s3/put_object.cpp)。

## 將字串上傳至儲存貯體
<a name="upload-object-string"></a>

使用 `S3Client` 物件`PutObject`函數，提供儲存貯體名稱、金鑰名稱和要上傳的檔案。儲存貯體必須存在，否則會產生錯誤。此範例使用 `Aws::StringStream`將記憶體內字串資料物件直接上傳至儲存貯體，與上一個範例不同。

如需非同步上傳物件的範例，請參閱 [使用 進行非同步程式設計 適用於 C\$1\$1 的 AWS SDK](async-methods.md)

 **Code** 

```
bool AwsDoc::S3::putObjectBuffer(const Aws::String &bucketName,
                                 const Aws::String &objectName,
                                 const std::string &objectContent,
                                 const Aws::S3::S3ClientConfiguration &clientConfig) {
    Aws::S3::S3Client s3Client(clientConfig);

    Aws::S3::Model::PutObjectRequest request;
    request.SetBucket(bucketName);
    request.SetKey(objectName);

    const std::shared_ptr<Aws::IOStream> inputData =
            Aws::MakeShared<Aws::StringStream>("");
    *inputData << objectContent.c_str();

    request.SetBody(inputData);

    Aws::S3::Model::PutObjectOutcome outcome = s3Client.PutObject(request);

    if (!outcome.IsSuccess()) {
        std::cerr << "Error: putObjectBuffer: " <<
                  outcome.GetError().GetMessage() << std::endl;
    } else {
        std::cout << "Success: Object '" << objectName << "' with content '"
                  << objectContent << "' uploaded to bucket '" << bucketName << "'.";
    }

    return outcome.IsSuccess();
}
```

請參閱 GitHub 上的[完整範例](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp/example_code/s3/put_object_buffer.cpp)。

## 列出物件
<a name="list-objects"></a>

若要取得儲存貯體中的物件清單，請使用 `S3Client` 物件`ListObjects`函數。提供您使用儲存貯體名稱設定的 `ListObjectsRequest` ，以列出 的內容。

`ListObjects` 函數會傳回`ListObjectsOutcome`物件，您可以用來取得`Object`執行個體形式的物件清單。

 **Code** 

```
bool AwsDoc::S3::listObjects(const Aws::String &bucketName,
                             Aws::Vector<Aws::String> &keysResult,
                             const Aws::S3::S3ClientConfiguration &clientConfig) {
    Aws::S3::S3Client s3Client(clientConfig);

    Aws::S3::Model::ListObjectsV2Request request;
    request.WithBucket(bucketName);

    Aws::String continuationToken; // Used for pagination.
    Aws::Vector<Aws::S3::Model::Object> allObjects;

    do {
        if (!continuationToken.empty()) {
            request.SetContinuationToken(continuationToken);
        }

        auto outcome = s3Client.ListObjectsV2(request);

        if (!outcome.IsSuccess()) {
            std::cerr << "Error: listObjects: " <<
                      outcome.GetError().GetMessage() << std::endl;
            return false;
        } else {
            Aws::Vector<Aws::S3::Model::Object> objects =
                    outcome.GetResult().GetContents();

            allObjects.insert(allObjects.end(), objects.begin(), objects.end());
            continuationToken = outcome.GetResult().GetNextContinuationToken();
        }
    } while (!continuationToken.empty());

    std::cout << allObjects.size() << " object(s) found:" << std::endl;

    for (const auto &object: allObjects) {
        std::cout << "  " << object.GetKey() << std::endl;
        keysResult.push_back(object.GetKey());
    }

    return true;
}
```

請參閱 GitHub 上的[完整範例](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp/example_code/s3/list_objects.cpp)。

## 下載物件
<a name="download-object"></a>

使用 `S3Client` 物件`GetObject`函數，傳遞`GetObjectRequest`您使用儲存貯體名稱和要下載的物件金鑰設定的 。 `GetObject`會傳回包含 [https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-s3/html/class_aws_1_1_s3_1_1_model_1_1_get_object_result.html](https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-s3/html/class_aws_1_1_s3_1_1_model_1_1_get_object_result.html)和 的[https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-s3/html/namespace_aws_1_1_s3_1_1_model.html#a6e16a7b25e8c7547934968a538a15272](https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-s3/html/namespace_aws_1_1_s3_1_1_model.html#a6e16a7b25e8c7547934968a538a15272)物件[https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-s3/html/class_aws_1_1_s3_1_1_s3_error.html](https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-s3/html/class_aws_1_1_s3_1_1_s3_error.html)。 `GetObjectResult` 可用來存取 S3 物件的資料。

下列範例會從 Amazon S3 下載物件。物件內容存放在本機變數中，內容的第一行會輸出到主控台。

 **Code** 

```
bool AwsDoc::S3::getObject(const Aws::String &objectKey,
                           const Aws::String &fromBucket,
                           const Aws::S3::S3ClientConfiguration &clientConfig) {
    Aws::S3::S3Client client(clientConfig);

    Aws::S3::Model::GetObjectRequest request;
    request.SetBucket(fromBucket);
    request.SetKey(objectKey);

    Aws::S3::Model::GetObjectOutcome outcome =
            client.GetObject(request);

    if (!outcome.IsSuccess()) {
        const Aws::S3::S3Error &err = outcome.GetError();
        std::cerr << "Error: getObject: " <<
                  err.GetExceptionName() << ": " << err.GetMessage() << std::endl;
    } else {
        std::cout << "Successfully retrieved '" << objectKey << "' from '"
                  << fromBucket << "'." << std::endl;
    }

    return outcome.IsSuccess();
}
```

請參閱 GitHub 上的[完整範例](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp/example_code/s3/get_object.cpp)。

## 刪除物件
<a name="delete-object"></a>

使用`S3Client`物件的 `DeleteObject`函數，傳遞`DeleteObjectRequest`您使用儲存貯體名稱和要下載的物件所設定的 。*指定的儲存貯體和物件金鑰必須存在，否則會產生錯誤*。

 **Code** 

```
bool AwsDoc::S3::deleteObject(const Aws::String &objectKey,
                              const Aws::String &fromBucket,
                              const Aws::S3::S3ClientConfiguration &clientConfig) {
    Aws::S3::S3Client client(clientConfig);
    Aws::S3::Model::DeleteObjectRequest request;

    request.WithKey(objectKey)
            .WithBucket(fromBucket);

    Aws::S3::Model::DeleteObjectOutcome outcome =
            client.DeleteObject(request);

    if (!outcome.IsSuccess()) {
        auto err = outcome.GetError();
        std::cerr << "Error: deleteObject: " <<
                  err.GetExceptionName() << ": " << err.GetMessage() << std::endl;
    } else {
        std::cout << "Successfully deleted the object." << std::endl;
    }

    return outcome.IsSuccess();
}
```

請參閱 GitHub 上的[完整範例](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp/example_code/s3/delete_object.cpp)。

# 管理 Amazon S3 存取許可
<a name="examples-s3-access-permissions"></a>

Amazon S3 儲存貯體或物件的存取許可是在存取控制清單 (ACL) 中定義。ACL 會指定儲存貯體/物件的擁有者，以及授予清單。每個授予都會指定使用者 （或承授者） 和使用者存取儲存貯體/物件的許可，例如讀取或寫入存取。

## 先決條件
<a name="codeExamplePrereq"></a>

開始之前，建議您先閱讀[開始使用 適用於 C\$1\$1 的 AWS SDK](getting-started.md)。

下載範例程式碼並建置解決方案，如中所述[程式碼範例入門](getting-started-code-examples.md)。

若要執行範例，您的程式碼用來提出請求的使用者描述檔必須具有 AWS （針對 服務和 動作） 的適當許可。如需詳細資訊，請參閱[提供 AWS 登入](credentials.md)資料。

## 管理物件的存取控制清單
<a name="manage-an-object-s-access-control-list"></a>

您可以透過呼叫`S3Client`方法 來擷取物件的存取控制清單`GetObjectAcl`。方法接受物件的名稱及其儲存貯體。傳回值包含 ACL 的 `Owner`和 清單`Grants`。

```
bool AwsDoc::S3::getObjectAcl(const Aws::String &bucketName,
                              const Aws::String &objectKey,
                              const Aws::S3::S3ClientConfiguration &clientConfig) {
    Aws::S3::S3Client s3Client(clientConfig);

    Aws::S3::Model::GetObjectAclRequest request;
    request.SetBucket(bucketName);
    request.SetKey(objectKey);

    Aws::S3::Model::GetObjectAclOutcome outcome =
            s3Client.GetObjectAcl(request);

    if (!outcome.IsSuccess()) {
        const Aws::S3::S3Error &err = outcome.GetError();
        std::cerr << "Error: getObjectAcl: "
                  << err.GetExceptionName() << ": " << err.GetMessage() << std::endl;
    } else {
        Aws::Vector<Aws::S3::Model::Grant> grants =
                outcome.GetResult().GetGrants();

        for (auto it = grants.begin(); it != grants.end(); it++) {
            std::cout << "For object " << objectKey << ": "
                      << std::endl << std::endl;

            Aws::S3::Model::Grant grant = *it;
            Aws::S3::Model::Grantee grantee = grant.GetGrantee();

            if (grantee.TypeHasBeenSet()) {
                std::cout << "Type:          "
                          << getGranteeTypeString(grantee.GetType()) << std::endl;
            }

            if (grantee.DisplayNameHasBeenSet()) {
                std::cout << "Display name:  "
                          << grantee.GetDisplayName() << std::endl;
            }

            if (grantee.EmailAddressHasBeenSet()) {
                std::cout << "Email address: "
                          << grantee.GetEmailAddress() << std::endl;
            }

            if (grantee.IDHasBeenSet()) {
                std::cout << "ID:            "
                          << grantee.GetID() << std::endl;
            }

            if (grantee.URIHasBeenSet()) {
                std::cout << "URI:           "
                          << grantee.GetURI() << std::endl;
            }

            std::cout << "Permission:    " <<
                      getPermissionString(grant.GetPermission()) <<
                      std::endl << std::endl;
        }
    }

    return outcome.IsSuccess();
}

//! Routine which converts a built-in type enumeration to a human-readable string.
/*!
 \param type: Type enumeration.
 \return String: Human-readable string
*/
Aws::String getGranteeTypeString(const Aws::S3::Model::Type &type) {
    switch (type) {
        case Aws::S3::Model::Type::AmazonCustomerByEmail:
            return "Email address of an AWS account";
        case Aws::S3::Model::Type::CanonicalUser:
            return "Canonical user ID of an AWS account";
        case Aws::S3::Model::Type::Group:
            return "Predefined Amazon S3 group";
        case Aws::S3::Model::Type::NOT_SET:
            return "Not set";
        default:
            return "Type unknown";
    }
}

//! Routine which converts a built-in type enumeration to a human-readable string.
/*!
 \param permission: Permission enumeration.
 \return String: Human-readable string
*/
Aws::String getPermissionString(const Aws::S3::Model::Permission &permission) {
    switch (permission) {
        case Aws::S3::Model::Permission::FULL_CONTROL:
            return "Can read this object's data and its metadata, "
                   "and read/write this object's permissions";
        case Aws::S3::Model::Permission::NOT_SET:
            return "Permission not set";
        case Aws::S3::Model::Permission::READ:
            return "Can read this object's data and its metadata";
        case Aws::S3::Model::Permission::READ_ACP:
            return "Can read this object's permissions";
            // case Aws::S3::Model::Permission::WRITE // Not applicable.
        case Aws::S3::Model::Permission::WRITE_ACP:
            return "Can write this object's permissions";
        default:
            return "Permission unknown";
    }
}
```

您可以透過建立新的 ACL 或變更目前 ACL 中指定的授予來修改 ACL。更新的 ACL 透過將其傳遞至 `PutObjectAcl`方法，成為新的目前 ACL。

下列程式碼使用 擷取的 ACL，`GetObjectAcl`並為其新增新的授權。使用者或承授者會獲得物件的 READ 許可。修改後的 ACL 會傳遞至 `PutObjectAcl`，使其成為新的目前 ACL。

```
bool AwsDoc::S3::putObjectAcl(const Aws::String &bucketName, const Aws::String &objectKey, const Aws::String &ownerID,
                              const Aws::String &granteePermission, const Aws::String &granteeType,
                              const Aws::String &granteeID, const Aws::String &granteeEmailAddress,
                              const Aws::String &granteeURI, const Aws::S3::S3ClientConfiguration &clientConfig) {
    Aws::S3::S3Client s3Client(clientConfig);

    Aws::S3::Model::Owner owner;
    owner.SetID(ownerID);

    Aws::S3::Model::Grantee grantee;
    grantee.SetType(setGranteeType(granteeType));

    if (!granteeEmailAddress.empty()) {
        grantee.SetEmailAddress(granteeEmailAddress);
    }

    if (!granteeID.empty()) {
        grantee.SetID(granteeID);
    }

    if (!granteeURI.empty()) {
        grantee.SetURI(granteeURI);
    }

    Aws::S3::Model::Grant grant;
    grant.SetGrantee(grantee);
    grant.SetPermission(setGranteePermission(granteePermission));

    Aws::Vector<Aws::S3::Model::Grant> grants;
    grants.push_back(grant);

    Aws::S3::Model::AccessControlPolicy acp;
    acp.SetOwner(owner);
    acp.SetGrants(grants);

    Aws::S3::Model::PutObjectAclRequest request;
    request.SetAccessControlPolicy(acp);
    request.SetBucket(bucketName);
    request.SetKey(objectKey);

    Aws::S3::Model::PutObjectAclOutcome outcome =
            s3Client.PutObjectAcl(request);

    if (!outcome.IsSuccess()) {
        auto error = outcome.GetError();
        std::cerr << "Error: putObjectAcl: " << error.GetExceptionName()
                  << " - " << error.GetMessage() << std::endl;
    } else {
        std::cout << "Successfully added an ACL to the object '" << objectKey
                  << "' in the bucket '" << bucketName << "'." << std::endl;
    }

    return outcome.IsSuccess();
}

//! Routine which converts a human-readable string to a built-in type enumeration.
/*!
 \param access: Human readable string.
 \return Permission: Permission enumeration.
*/
Aws::S3::Model::Permission setGranteePermission(const Aws::String &access) {
    if (access == "FULL_CONTROL")
        return Aws::S3::Model::Permission::FULL_CONTROL;
    if (access == "WRITE")
        return Aws::S3::Model::Permission::WRITE;
    if (access == "READ")
        return Aws::S3::Model::Permission::READ;
    if (access == "WRITE_ACP")
        return Aws::S3::Model::Permission::WRITE_ACP;
    if (access == "READ_ACP")
        return Aws::S3::Model::Permission::READ_ACP;
    return Aws::S3::Model::Permission::NOT_SET;
}

//! Routine which converts a human-readable string to a built-in type enumeration.
/*!
 \param type: Human readable string.
 \return Type: Type enumeration.
*/
Aws::S3::Model::Type setGranteeType(const Aws::String &type) {
    if (type == "Amazon customer by email")
        return Aws::S3::Model::Type::AmazonCustomerByEmail;
    if (type == "Canonical user")
        return Aws::S3::Model::Type::CanonicalUser;
    if (type == "Group")
        return Aws::S3::Model::Type::Group;
    return Aws::S3::Model::Type::NOT_SET;
}
```

請參閱 GitHub 上的[完整範例](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp/example_code/s3/get_put_object_acl.cpp)。

## 管理儲存貯體的存取控制清單
<a name="manage-a-bucket-s-access-control-list"></a>

在大多數情況下，設定儲存貯體存取許可的偏好方法是定義儲存貯體政策。不過，儲存貯體也支援希望使用它們的使用者的存取控制清單。

儲存貯體存取控制清單的管理與用於物件的存取控制清單相同。`GetBucketAcl` 方法會擷取儲存貯體目前的 ACL，並將新的 ACL `PutBucketAcl`套用至儲存貯體。

下列程式碼示範取得和設定儲存貯體 ACL。

```
//! Routine which demonstrates setting the ACL for an S3 bucket.
/*!
  \param bucketName: Name of a bucket.
  \param ownerID: The canonical ID of the bucket owner.
   See https://docs.aws.amazon.com/AmazonS3/latest/userguide/finding-canonical-user-id.html for more information.
  \param granteePermission: The access level to enable for the grantee.
  \param granteeType: The type of grantee.
  \param granteeID: The canonical ID of the grantee.
  \param granteeEmailAddress: The email address associated with the grantee's AWS account.
  \param granteeURI: The URI of a built-in access group.
  \param clientConfig: Aws client configuration.
  \return bool: Function succeeded.
*/

bool AwsDoc::S3::getPutBucketAcl(const Aws::String &bucketName,
                                 const Aws::String &ownerID,
                                 const Aws::String &granteePermission,
                                 const Aws::String &granteeType,
                                 const Aws::String &granteeID,
                                 const Aws::String &granteeEmailAddress,
                                 const Aws::String &granteeURI,
                                 const Aws::S3::S3ClientConfiguration &clientConfig) {
    bool result = ::putBucketAcl(bucketName, ownerID, granteePermission, granteeType,
                                 granteeID,
                                 granteeEmailAddress,
                                 granteeURI,
                                 clientConfig);
    if (result) {
        result = ::getBucketAcl(bucketName, clientConfig);
    }

    return result;
}

//! Routine which demonstrates setting the ACL for an S3 bucket.
/*!
  \param bucketName: Name of from bucket.
  \param ownerID: The canonical ID of the bucket owner.
   See https://docs.aws.amazon.com/AmazonS3/latest/userguide/finding-canonical-user-id.html for more information.
  \param granteePermission: The access level to enable for the grantee.
  \param granteeType: The type of grantee.
  \param granteeID: The canonical ID of the grantee.
  \param granteeEmailAddress: The email address associated with the grantee's AWS account.
  \param granteeURI: The URI of a built-in access group.
  \param clientConfig: Aws client configuration.
  \return bool: Function succeeded.
*/

bool putBucketAcl(const Aws::String &bucketName,
                  const Aws::String &ownerID,
                  const Aws::String &granteePermission,
                  const Aws::String &granteeType,
                  const Aws::String &granteeID,
                  const Aws::String &granteeEmailAddress,
                  const Aws::String &granteeURI,
                  const Aws::S3::S3ClientConfiguration &clientConfig) {
    Aws::S3::S3Client s3Client(clientConfig);

    Aws::S3::Model::Owner owner;
    owner.SetID(ownerID);

    Aws::S3::Model::Grantee grantee;
    grantee.SetType(setGranteeType(granteeType));

    if (!granteeEmailAddress.empty()) {
        grantee.SetEmailAddress(granteeEmailAddress);
    }

    if (!granteeID.empty()) {
        grantee.SetID(granteeID);
    }

    if (!granteeURI.empty()) {
        grantee.SetURI(granteeURI);
    }

    Aws::S3::Model::Grant grant;
    grant.SetGrantee(grantee);
    grant.SetPermission(setGranteePermission(granteePermission));

    Aws::Vector<Aws::S3::Model::Grant> grants;
    grants.push_back(grant);

    Aws::S3::Model::AccessControlPolicy acp;
    acp.SetOwner(owner);
    acp.SetGrants(grants);

    Aws::S3::Model::PutBucketAclRequest request;
    request.SetAccessControlPolicy(acp);
    request.SetBucket(bucketName);

    Aws::S3::Model::PutBucketAclOutcome outcome =
            s3Client.PutBucketAcl(request);

    if (!outcome.IsSuccess()) {
        const Aws::S3::S3Error &error = outcome.GetError();

        std::cerr << "Error: putBucketAcl: " << error.GetExceptionName()
                  << " - " << error.GetMessage() << std::endl;
    } else {
        std::cout << "Successfully added an ACL to the bucket '" << bucketName
                  << "'." << std::endl;
    }

    return outcome.IsSuccess();
}

//! Routine which demonstrates getting the ACL for an S3 bucket.
/*!
  \param bucketName: Name of the s3 bucket.
  \param clientConfig: Aws client configuration.
  \return bool: Function succeeded.
*/
bool getBucketAcl(const Aws::String &bucketName,
                  const Aws::S3::S3ClientConfiguration &clientConfig) {
    Aws::S3::S3Client s3Client(clientConfig);

    Aws::S3::Model::GetBucketAclRequest request;
    request.SetBucket(bucketName);

    Aws::S3::Model::GetBucketAclOutcome outcome =
            s3Client.GetBucketAcl(request);

    if (!outcome.IsSuccess()) {
        const Aws::S3::S3Error &err = outcome.GetError();
        std::cerr << "Error: getBucketAcl: "
                  << err.GetExceptionName() << ": " << err.GetMessage() << std::endl;
    } else {
        const Aws::Vector<Aws::S3::Model::Grant> &grants =
                outcome.GetResult().GetGrants();

        for (const Aws::S3::Model::Grant &grant: grants) {
            const Aws::S3::Model::Grantee &grantee = grant.GetGrantee();

            std::cout << "For bucket " << bucketName << ": "
                      << std::endl << std::endl;

            if (grantee.TypeHasBeenSet()) {
                std::cout << "Type:          "
                          << getGranteeTypeString(grantee.GetType()) << std::endl;
            }

            if (grantee.DisplayNameHasBeenSet()) {
                std::cout << "Display name:  "
                          << grantee.GetDisplayName() << std::endl;
            }

            if (grantee.EmailAddressHasBeenSet()) {
                std::cout << "Email address: "
                          << grantee.GetEmailAddress() << std::endl;
            }

            if (grantee.IDHasBeenSet()) {
                std::cout << "ID:            "
                          << grantee.GetID() << std::endl;
            }

            if (grantee.URIHasBeenSet()) {
                std::cout << "URI:           "
                          << grantee.GetURI() << std::endl;
            }

            std::cout << "Permission:    " <<
                      getPermissionString(grant.GetPermission()) <<
                      std::endl << std::endl;
        }
    }

    return outcome.IsSuccess();
}

//! Routine which converts a built-in type enumeration to a human-readable string.
/*!
 \param permission: Permission enumeration.
 \return String: Human-readable string.
*/

Aws::String getPermissionString(const Aws::S3::Model::Permission &permission) {
    switch (permission) {
        case Aws::S3::Model::Permission::FULL_CONTROL:
            return "Can list objects in this bucket, create/overwrite/delete "
                   "objects in this bucket, and read/write this "
                   "bucket's permissions";
        case Aws::S3::Model::Permission::NOT_SET:
            return "Permission not set";
        case Aws::S3::Model::Permission::READ:
            return "Can list objects in this bucket";
        case Aws::S3::Model::Permission::READ_ACP:
            return "Can read this bucket's permissions";
        case Aws::S3::Model::Permission::WRITE:
            return "Can create, overwrite, and delete objects in this bucket";
        case Aws::S3::Model::Permission::WRITE_ACP:
            return "Can write this bucket's permissions";
        default:
            return "Permission unknown";
    }
}

//! Routine which converts a human-readable string to a built-in type enumeration
/*!
 \param access: Human readable string.
 \return Permission: Permission enumeration.
*/
Aws::S3::Model::Permission setGranteePermission(const Aws::String &access) {
    if (access == "FULL_CONTROL")
        return Aws::S3::Model::Permission::FULL_CONTROL;
    if (access == "WRITE")
        return Aws::S3::Model::Permission::WRITE;
    if (access == "READ")
        return Aws::S3::Model::Permission::READ;
    if (access == "WRITE_ACP")
        return Aws::S3::Model::Permission::WRITE_ACP;
    if (access == "READ_ACP")
        return Aws::S3::Model::Permission::READ_ACP;
    return Aws::S3::Model::Permission::NOT_SET;
}

//! Routine which converts a built-in type enumeration to a human-readable string.
/*!
 \param type: Type enumeration.
 \return bool: Human-readable string.
*/
Aws::String getGranteeTypeString(const Aws::S3::Model::Type &type) {
    switch (type) {
        case Aws::S3::Model::Type::AmazonCustomerByEmail:
            return "Email address of an AWS account";
        case Aws::S3::Model::Type::CanonicalUser:
            return "Canonical user ID of an AWS account";
        case Aws::S3::Model::Type::Group:
            return "Predefined Amazon S3 group";
        case Aws::S3::Model::Type::NOT_SET:
            return "Not set";
        default:
            return "Type unknown";
    }
}

Aws::S3::Model::Type setGranteeType(const Aws::String &type) {
    if (type == "Amazon customer by email")
        return Aws::S3::Model::Type::AmazonCustomerByEmail;
    if (type == "Canonical user")
        return Aws::S3::Model::Type::CanonicalUser;
    if (type == "Group")
        return Aws::S3::Model::Type::Group;
    return Aws::S3::Model::Type::NOT_SET;
}
```

請參閱 GitHub 上的[完整範例](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp/example_code/s3/get_put_bucket_acl.cpp)。

# 使用儲存貯體政策管理對 Amazon S3 儲存貯體的存取
<a name="examples-s3-bucket-policies"></a>

您可以設定、取得或刪除儲存*貯體政策*，以管理對 Amazon S3 儲存貯體的存取。

## 先決條件
<a name="codeExamplePrereq"></a>

開始之前，建議您先閱讀[開始使用 適用於 C\$1\$1 的 AWS SDK](getting-started.md)。

下載範例程式碼並建置解決方案，如中所述[程式碼範例入門](getting-started-code-examples.md)。

若要執行範例，您的程式碼用來提出請求的使用者描述檔必須具有 AWS （針對 服務和 動作） 的適當許可。如需詳細資訊，請參閱[提供 AWS 登入](credentials.md)資料。

## 設定儲存貯體政策
<a name="set-s3-bucket-policy"></a>

您可以呼叫 `S3Client`的 `PutBucketPolicy`函數，並在 [PutBucketPolicyRequest](https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-s3/html/class_aws_1_1_s3_1_1_model_1_1_put_bucket_policy_request.html) 中提供儲存貯體名稱和政策的 JSON 表示法，來設定特定 S3 儲存貯體的儲存貯體政策。

 **Code** 

```
//! Build a policy JSON string.
/*!
  \param userArn: Aws user Amazon Resource Name (ARN).
      For more information, see https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_identifiers.html#identifiers-arns.
  \param bucketName: Name of a bucket.
  \return String: Policy as JSON string.
*/

Aws::String getPolicyString(const Aws::String &userArn,
                            const Aws::String &bucketName) {
    return
            "{\n"
            "   \"Version\":\"2012-10-17\",\n"
            "   \"Statement\":[\n"
            "       {\n"
            "           \"Sid\": \"1\",\n"
            "           \"Effect\": \"Allow\",\n"
            "           \"Principal\": {\n"
            "               \"AWS\": \""
            + userArn +
            "\"\n""           },\n"
            "           \"Action\": [ \"s3:getObject\" ],\n"
            "           \"Resource\": [ \"arn:aws:s3:::"
            + bucketName +
            "/*\" ]\n"
            "       }\n"
            "   ]\n"
            "}";
}
```

```
bool AwsDoc::S3::putBucketPolicy(const Aws::String &bucketName,
                                 const Aws::String &policyBody,
                                 const Aws::S3::S3ClientConfiguration &clientConfig) {
    Aws::S3::S3Client s3Client(clientConfig);

    std::shared_ptr<Aws::StringStream> request_body =
            Aws::MakeShared<Aws::StringStream>("");
    *request_body << policyBody;

    Aws::S3::Model::PutBucketPolicyRequest request;
    request.SetBucket(bucketName);
    request.SetBody(request_body);

    Aws::S3::Model::PutBucketPolicyOutcome outcome =
            s3Client.PutBucketPolicy(request);

    if (!outcome.IsSuccess()) {
        std::cerr << "Error: putBucketPolicy: "
                  << outcome.GetError().GetMessage() << std::endl;
    } else {
        std::cout << "Set the following policy body for the bucket '" <<
                  bucketName << "':" << std::endl << std::endl;
        std::cout << policyBody << std::endl;
    }

    return outcome.IsSuccess();
}
```

**注意**  
[Aws：：Utils：：Json：：JsonValue](https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-core/html/class_aws_1_1_utils_1_1_json_1_1_json_value.html) 公用程式類別可用來協助您建構有效的 JSON 物件以傳遞至 `PutBucketPolicy`。

請參閱 GitHub 上的[完整範例](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp/example_code/s3/put_bucket_policy.cpp)。

## 取得儲存貯體政策
<a name="get-s3-bucket-policy"></a>

若要擷取 Amazon S3 儲存貯體的政策，請呼叫 `S3Client`的 `GetBucketPolicy`函數，並在 [GetBucketPolicyRequest](https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-s3/html/class_aws_1_1_s3_1_1_model_1_1_get_bucket_policy_request.html) 中傳遞儲存貯體的名稱。

 **Code** 

```
bool AwsDoc::S3::getBucketPolicy(const Aws::String &bucketName,
                                 const Aws::S3::S3ClientConfiguration &clientConfig) {
    Aws::S3::S3Client s3Client(clientConfig);

    Aws::S3::Model::GetBucketPolicyRequest request;
    request.SetBucket(bucketName);

    Aws::S3::Model::GetBucketPolicyOutcome outcome =
            s3Client.GetBucketPolicy(request);

    if (!outcome.IsSuccess()) {
        const Aws::S3::S3Error &err = outcome.GetError();
        std::cerr << "Error: getBucketPolicy: "
                  << err.GetExceptionName() << ": " << err.GetMessage() << std::endl;
    } else {
        Aws::StringStream policy_stream;
        Aws::String line;

        outcome.GetResult().GetPolicy() >> line;
        policy_stream << line;

        std::cout << "Retrieve the policy for bucket '" << bucketName << "':\n\n" <<
                  policy_stream.str() << std::endl;
    }

    return outcome.IsSuccess();
}
```

請參閱 GitHub 上的[完整範例](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp/example_code/s3/get_bucket_policy.cpp)。

## 刪除儲存貯體政策
<a name="delete-s3-bucket-policy"></a>

若要刪除儲存貯體政策，請呼叫 `S3Client`的 `DeleteBucketPolicy`函數，在 [DeleteBucketPolicyRequest](https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-s3/html/class_aws_1_1_s3_1_1_model_1_1_delete_bucket_policy_request.html) 中提供儲存貯體名稱。

 **Code** 

```
bool AwsDoc::S3::deleteBucketPolicy(const Aws::String &bucketName,
                                    const Aws::S3::S3ClientConfiguration &clientConfig) {
    Aws::S3::S3Client client(clientConfig);

    Aws::S3::Model::DeleteBucketPolicyRequest request;
    request.SetBucket(bucketName);

    Aws::S3::Model::DeleteBucketPolicyOutcome outcome = client.DeleteBucketPolicy(request);

    if (!outcome.IsSuccess()) {
        const Aws::S3::S3Error &err = outcome.GetError();
        std::cerr << "Error: deleteBucketPolicy: " <<
                  err.GetExceptionName() << ": " << err.GetMessage() << std::endl;
    } else {
        std::cout << "Policy was deleted from the bucket." << std::endl;
    }

    return outcome.IsSuccess();
}
```

即使儲存貯體還沒有政策，此函數也會成功。如果您指定不存在的儲存貯體名稱，或如果您無法存取儲存貯體，`AmazonServiceException`則會擲出 。

請參閱 GitHub 上的[完整範例](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp/example_code/s3/delete_bucket_policy.cpp)。

## 詳細資訊
<a name="more-info"></a>
+  Amazon Simple Storage Service API 參考中的 [PutBucketPolicy](https://docs.aws.amazon.com/AmazonS3/latest/API/PutBucketPolicy.html) 
+  Amazon Simple Storage Service API 參考中的 [GetBucketPolicy](https://docs.aws.amazon.com/AmazonS3/latest/API/GetBucketPolicy.html) 
+  Amazon Simple Storage Service API 參考中的 [DeleteBucketPolicy](https://docs.aws.amazon.com/AmazonS3/latest/API/DeleteBucketPolicy.html) 
+  《Amazon Simple Storage Service 使用者指南》中的[存取政策語言概觀](https://docs.aws.amazon.com/AmazonS3/latest/dev/access-policy-language-overview.html) 
+  《Amazon Simple Storage Service 使用者指南》中的[儲存貯體政策範例](https://docs.aws.amazon.com/AmazonS3/latest/dev/example-bucket-policies.html) 

# 將 Amazon S3 儲存貯體設定為網站
<a name="examples-s3-website-configuration"></a>

您可以設定 Amazon S3 儲存貯體做為網站運作。若要這樣做，您需要設定其網站組態。

## 先決條件
<a name="codeExamplePrereq"></a>

開始之前，建議您先閱讀[開始使用 適用於 C\$1\$1 的 AWS SDK](getting-started.md)。

下載範例程式碼並建置解決方案，如中所述[程式碼範例入門](getting-started-code-examples.md)。

若要執行範例，您的程式碼用來提出請求的使用者描述檔必須具有 AWS （針對 服務和 動作） 的適當許可。如需詳細資訊，請參閱[提供 AWS 登入](credentials.md)資料。

## 設定儲存貯體的網站組態
<a name="set-a-bucket-s-website-configuration"></a>

若要設定 Amazon S3 儲存貯體的網站組態，請使用 [WebsiteConfiguration](https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-s3/html/class_aws_1_1_s3_1_1_model_1_1_website_configuration.html) 物件中提供的 [PutBucketWebsiteRequest](https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-s3/html/class_aws_1_1_s3_1_1_model_1_1_put_bucket_website_request.html) 物件來呼叫 `S3Client`的 `PutBucketWebsite`函數，其中包含儲存貯體名稱及其網站組態。

*需要*設定索引文件；所有其他參數都是選用的。

 **Code** 

```
bool AwsDoc::S3::putWebsiteConfig(const Aws::String &bucketName,
                                  const Aws::String &indexPage, const Aws::String &errorPage,
                                  const Aws::S3::S3ClientConfiguration &clientConfig) {
    Aws::S3::S3Client client(clientConfig);

    Aws::S3::Model::IndexDocument indexDocument;
    indexDocument.SetSuffix(indexPage);

    Aws::S3::Model::ErrorDocument errorDocument;
    errorDocument.SetKey(errorPage);

    Aws::S3::Model::WebsiteConfiguration websiteConfiguration;
    websiteConfiguration.SetIndexDocument(indexDocument);
    websiteConfiguration.SetErrorDocument(errorDocument);

    Aws::S3::Model::PutBucketWebsiteRequest request;
    request.SetBucket(bucketName);
    request.SetWebsiteConfiguration(websiteConfiguration);

    Aws::S3::Model::PutBucketWebsiteOutcome outcome =
            client.PutBucketWebsite(request);

    if (!outcome.IsSuccess()) {
        std::cerr << "Error: PutBucketWebsite: "
                  << outcome.GetError().GetMessage() << std::endl;
    } else {
        std::cout << "Success: Set website configuration for bucket '"
                  << bucketName << "'." << std::endl;
    }

    return outcome.IsSuccess();
}
```

**注意**  
設定網站組態不會修改儲存貯體的存取許可。若要在 Web 上顯示您的檔案，您還需要設定儲存*貯體政策*，以允許公開讀取存取儲存貯體中的檔案。如需詳細資訊，請參閱[使用儲存貯體政策管理對 Amazon S3 儲存貯體的存取](examples-s3-bucket-policies.md)。

請參閱 GitHub 上的[完整範例](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp/example_code/s3/put_website_config.cpp)。

## 取得儲存貯體的網站組態
<a name="get-a-bucket-s-website-configuration"></a>

若要取得 Amazon S3 儲存貯體的網站組態，請使用 [GetBucketWebsiteRequest](https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-s3/html/class_aws_1_1_s3_1_1_model_1_1_get_bucket_website_request.html) 呼叫 `S3Client`的 `GetBucketWebsite`函數，其中包含要擷取組態的儲存貯體名稱。

組態會在結果物件中傳回為 [GetBucketWebsiteResult](https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-s3/html/class_aws_1_1_s3_1_1_model_1_1_get_bucket_website_result.html) 物件。如果儲存貯體沒有網站組態，`null`則會傳回 。

 **Code** 

```
bool AwsDoc::S3::getWebsiteConfig(const Aws::String &bucketName,
                                  const Aws::S3::S3ClientConfiguration &clientConfig) {
    Aws::S3::S3Client s3Client(clientConfig);

    Aws::S3::Model::GetBucketWebsiteRequest request;
    request.SetBucket(bucketName);

    Aws::S3::Model::GetBucketWebsiteOutcome outcome =
            s3Client.GetBucketWebsite(request);

    if (!outcome.IsSuccess()) {
        const Aws::S3::S3Error &err = outcome.GetError();

        std::cerr << "Error: GetBucketWebsite: "
                  << err.GetMessage() << std::endl;
    } else {
        Aws::S3::Model::GetBucketWebsiteResult websiteResult = outcome.GetResult();

        std::cout << "Success: GetBucketWebsite: "
                  << std::endl << std::endl
                  << "For bucket '" << bucketName << "':"
                  << std::endl
                  << "Index page : "
                  << websiteResult.GetIndexDocument().GetSuffix()
                  << std::endl
                  << "Error page: "
                  << websiteResult.GetErrorDocument().GetKey()
                  << std::endl;
    }

    return outcome.IsSuccess();
}
```

請參閱 GitHub 上的[完整範例](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp/example_code/s3/get_website_config.cpp)。

## 刪除儲存貯體的網站組態
<a name="delete-a-bucket-s-website-configuration"></a>

若要刪除 Amazon S3 儲存貯體的網站組態，請使用 [DeleteBucketWebsiteRequest](https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-s3/html/class_aws_1_1_s3_1_1_model_1_1_delete_bucket_website_request.html) 呼叫 `S3Client`的 `DeleteBucketWebsite`函數：包含要從中刪除組態的儲存貯體名稱。

 **Code** 

```
bool AwsDoc::S3::deleteBucketWebsite(const Aws::String &bucketName,
                                     const Aws::S3::S3ClientConfiguration &clientConfig) {
    Aws::S3::S3Client client(clientConfig);
    Aws::S3::Model::DeleteBucketWebsiteRequest request;
    request.SetBucket(bucketName);

    Aws::S3::Model::DeleteBucketWebsiteOutcome outcome =
            client.DeleteBucketWebsite(request);

    if (!outcome.IsSuccess()) {
        auto err = outcome.GetError();
        std::cerr << "Error: deleteBucketWebsite: " <<
                  err.GetExceptionName() << ": " << err.GetMessage() << std::endl;
    } else {
        std::cout << "Website configuration was removed." << std::endl;
    }

    return outcome.IsSuccess();
}
```

請參閱 GitHub 上的[完整範例](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp/example_code/s3/delete_website_config.cpp)。

## 詳細資訊
<a name="more-information"></a>
+  Amazon Simple Storage Service API 參考中的 [PUT 儲存貯體網站](https://docs.aws.amazon.com/AmazonS3/latest/API/RESTBucketPUTwebsite.html) 
+  Amazon Simple Storage Service API 參考中的 [GET 儲存貯體網站](https://docs.aws.amazon.com/AmazonS3/latest/API/RESTBucketGETwebsite.html) 
+  Amazon Simple Storage Service API 參考中的 [DELETE 儲存貯體網站](https://docs.aws.amazon.com/AmazonS3/latest/API/RESTBucketDELETEwebsite.html) 

# 將 TransferManager 用於 Amazon S3 操作
<a name="examples-s3-transfermanager"></a>

您可以使用 適用於 C\$1\$1 的 AWS SDK `TransferManager`類別可靠地將檔案從本機環境傳輸到 Amazon S3，並將物件從一個 Amazon S3 位置複製到另一個位置。 `TransferManager`可以取得傳輸進度，並暫停或繼續上傳和下載。

**注意**  
為了避免收取不完整或部分上傳的費用，建議您在 Amazon S3 儲存貯體上啟用 [AbortIncompleteMultipartUpload](https://docs.aws.amazon.com/AmazonS3/latest/userguide/mpu-abort-incomplete-mpu-lifecycle-config.html) 生命週期規則。  
此規則會指示 Amazon S3 在啟動後的指定天數內中止未完成的分段上傳。超過設定的時間限制時，Amazon S3 會中止上傳，然後刪除不完整的上傳資料。  
如需詳細資訊，請參閱《Amazon S3 使用者指南》中的在[儲存貯體上設定生命週期組態](https://docs.aws.amazon.com/AmazonS3/latest/userguide/how-to-set-lifecycle-configuration-intro.html)。

## 先決條件
<a name="codeExamplePrereq"></a>

開始之前，建議您先閱讀[開始使用 適用於 C\$1\$1 的 AWS SDK](getting-started.md)。

下載範例程式碼並建置解決方案，如中所述[程式碼範例入門](getting-started-code-examples.md)。

若要執行範例，您的程式碼用來提出請求的使用者描述檔必須具有 AWS （針對 服務和 動作） 的適當許可。如需詳細資訊，請參閱[提供 AWS 登入](credentials.md)資料。

## 使用 上傳和下載物件 `TransferManager`
<a name="stream"></a>

此範例示範如何在記憶體中[https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-transfer/html/class_aws_1_1_transfer_1_1_transfer_manager.html](https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-transfer/html/class_aws_1_1_transfer_1_1_transfer_manager.html)傳輸大型物件。 `UploadFile`和 `DownloadFile`方法會以非同步方式呼叫，並傳回 `TransferHandle`來管理請求的狀態。如果上傳的物件大於 `bufferSize`，則會執行分段上傳。`bufferSize` 預設為 5MB，但可以透過 設定[https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-transfer/html/struct_aws_1_1_transfer_1_1_transfer_manager_configuration.html](https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-transfer/html/struct_aws_1_1_transfer_1_1_transfer_manager_configuration.html)。

```
        auto s3_client = Aws::MakeShared<Aws::S3::S3Client>("S3Client");
        auto executor = Aws::MakeShared<Aws::Utils::Threading::PooledThreadExecutor>("executor", 25);
        Aws::Transfer::TransferManagerConfiguration transfer_config(executor.get());
        transfer_config.s3Client = s3_client;

        // Create buffer to hold data received by the data stream.
        Aws::Utils::Array<unsigned char> buffer(BUFFER_SIZE);

        // The local variable 'streamBuffer' is captured by reference in a lambda.
        // It must persist until all downloading by the 'transfer_manager' is complete.
        Stream::PreallocatedStreamBuf streamBuffer(buffer.GetUnderlyingData(), buffer.GetLength());

        auto transfer_manager = Aws::Transfer::TransferManager::Create(transfer_config);

        auto uploadHandle = transfer_manager->UploadFile(LOCAL_FILE, BUCKET, KEY, "text/plain", Aws::Map<Aws::String, Aws::String>());
        uploadHandle->WaitUntilFinished();
        bool success = uploadHandle->GetStatus() == Transfer::TransferStatus::COMPLETED; 
      
        if (!success)
        {
            auto err = uploadHandle->GetLastError();           
            std::cout << "File upload failed:  "<< err.GetMessage() << std::endl;
        }
        else
        {
            std::cout << "File upload finished." << std::endl;

            auto downloadHandle = transfer_manager->DownloadFile(BUCKET,
                KEY,
                [&]() { //Define a lambda expression for the callback method parameter to stream back the data.
                    return Aws::New<MyUnderlyingStream>("TestTag", &streamBuffer);
                });
            downloadHandle->WaitUntilFinished();// Block calling thread until download is complete.
            auto downStat = downloadHandle->GetStatus();
            if (downStat != Transfer::TransferStatus::COMPLETED)
            {
                auto err = downloadHandle->GetLastError();
                std::cout << "File download failed:  " << err.GetMessage() << std::endl;
            }
            std::cout << "File download to memory finished."  << std::endl;
```

請參閱 GitHub 上的[完整範例](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp/example_code/transfer-manager/transferOnStream.cpp)。

# 使用 `S3CrtClient`進行 Amazon S3 操作
<a name="examples-s3-crt"></a>

`S3CrtClient` 類別可在 的 1.9 版中使用， 適用於 C\$1\$1 的 AWS SDK 並改善在 Amazon S3 之間上傳和下載大型資料檔案的輸送量。如需此版本改進的詳細資訊，請參閱[使用 v1 適用於 C\$1\$1 的 AWS SDK .9 改善 Amazon S3 輸送量 ](https://github.com/aws/aws-sdk-cpp/wiki/Improving-S3-Throughput-with-AWS-SDK-for-CPP-v1.9)

在[AWS 通用執行期 (CRT) 程式庫](https://docs.aws.amazon.com/sdkref/latest/guide/common-runtime.html)的頂端`S3CrtClient`實作 。

**注意**  
為了避免收取不完整或部分上傳的費用，建議您在 Amazon S3 儲存貯體上啟用 [AbortIncompleteMultipartUpload](https://docs.aws.amazon.com/AmazonS3/latest/userguide/mpu-abort-incomplete-mpu-lifecycle-config.html) 生命週期規則。  
此規則會指示 Amazon S3 在啟動後的指定天數內中止未完成的分段上傳。超過設定的時間限制時，Amazon S3 會中止上傳，然後刪除不完整的上傳資料。  
如需詳細資訊，請參閱《Amazon S3 使用者指南》中的在[儲存貯體上設定生命週期組態](https://docs.aws.amazon.com/AmazonS3/latest/userguide/how-to-set-lifecycle-configuration-intro.html)。

## 先決條件
<a name="codeExamplePrereq"></a>

開始之前，建議您先閱讀[開始使用 適用於 C\$1\$1 的 AWS SDK](getting-started.md)。

下載範例程式碼並建置解決方案，如中所述[程式碼範例入門](getting-started-code-examples.md)。

若要執行範例，您的程式碼用來提出請求的使用者描述檔必須具有 AWS （針對 服務和 動作） 的適當許可。如需詳細資訊，請參閱[提供 AWS 登入](credentials.md)資料。

## 使用 上傳和下載物件 `S3CrtClient`
<a name="stream"></a>

此範例示範如何使用 [https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-s3-crt/html/class_aws_1_1_s3_crt_1_1_s3_crt_client.html](https://docs.aws.amazon.com/sdk-for-cpp/latest/api/aws-cpp-sdk-s3-crt/html/class_aws_1_1_s3_crt_1_1_s3_crt_client.html)。此範例會建立儲存貯體、上傳物件、下載物件，然後刪除檔案和儲存貯體。PUT 操作會變成分段上傳。GET 操作會變成多個「範圍」的 GET 請求。如需分段上傳的詳細資訊，請參閱《Amazon S3 使用者指南》中的[使用分段上傳上傳和複製物件](https://docs.aws.amazon.com/AmazonS3/latest/userguide/mpuoverview.html)。

在此範例中，提供的資料檔案 `ny.json`會以分段上傳的形式上傳。這可以透過在成功執行程式後檢視偵錯日誌來確認。

如果上傳失敗，`AbortMultipartUpload`則會在基礎 CRT 程式庫中發出 ，以清除任何已上傳的組件。不過，並非所有故障都可以在內部處理 （例如網路纜線已拔除）。建議您在 Amazon S3 儲存貯體上建立生命週期規則，以確保部分上傳的資料不會停留在您的帳戶 （部分上傳的資料仍應計費）。若要了解如何設定生命週期規則，請參閱[探索和刪除不完整的分段上傳以降低 Amazon S3 成本](https://aws.amazon.com/blogs/aws-cost-management/discovering-and-deleting-incomplete-multipart-uploads-to-lower-amazon-s3-costs/ )。

**使用偵錯日誌來探索分段上傳詳細資訊**

1. 在 中`main()`，請注意有「TODO」註解，其中包含更新程式碼的指示。

   1. 對於 `file_name`：從程式碼註解中提供的連結下載範例資料檔案 `ny.json`，或使用您自己的大型資料檔案。

   1. 對於 `region`：使用列舉將`region`變數更新為 AWS 區域 帳戶的 。若要尋找您帳戶的 區域，請登入 AWS 管理主控台，並在右上角找到 區域。

1. 建置範例。

1. 將變數指定的檔案複製到`file_name`可執行檔資料夾，然後執行`s3-crt-demo`可執行檔。

1. 在您的可執行檔資料夾中，尋找最新的 `.log` 檔案。

1. 開啟日誌檔案，選取**搜尋**，然後輸入 **partNumber**。

1. 日誌包含類似下列的項目，其中`uploadId`會針對上傳檔案的每個部分指定 `partNumber`和 ：

    `PUT /my-object partNumber=1&uploadId=gsk8vDbmnlA5EseDo._LDEgq22Qmt0SeuszYxMsZ9ABt503VqDIFOP8xzZI1P0zp.ToS.qo5kK16HNWogZF3KpRo.Dc7QnLZIK0BTmzCWwWoPax4T21hvP6nPdz9591F content-length:8388608 host:my-bucketasdfasdf.s3.us-east-2.amazonaws.com x-amz-content-sha256:UNSIGNED-PAYLOAD`

    及 

    `PUT /my-object partNumber=2&uploadId=gsk8vDbmnlA5EseDo._LDEgq22Qmt0SeuszYxMsZ9ABt503VqDIFOP8xzZI1P0zp.ToS.qo5kK16HNWogZF3KpRo.Dc7QnLZIK0BTmzCWwWoPax4T21hvP6nPdz9591F content-length:8388608 host:my-bucketasdfasdf.s3.us-east-2.amazonaws.com x-amz-content-sha256:UNSIGNED-PAYLOAD `

請參閱 GitHub 上的[完整範例](https://github.com/awsdocs/aws-doc-sdk-examples/tree/main/cpp/example_code/s3-crt/s3-crt-demo.cpp)。