

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

# CodeBuild 的「將 Docker 映像發佈至 Amazon ECR 映像儲存庫」範例
<a name="sample-docker"></a>

此範例會產生建置輸出 Docker 映像，然後將 Docker 映像推送至 Amazon Elastic Container Registry (Amazon ECR) 映像儲存庫。您可以調整此範例將 Docker 影像推送至 Docker Hub。如需詳細資訊，請參閱[將 'Publish Docker 映像修改為 Amazon ECR' 範例，以推送至 Docker Hub](sample-docker-docker-hub.md)。

若要了解如何使用自訂 Docker 建置映像 (Docker Hub 中的 `docker:dind`) 來建置 Docker 映像，請參閱我們的[自訂映像中的 Docker 範例](sample-docker-custom-image.md)。

已參考 `golang:1.12` 來測試過此範例。

此範例使用新的多階段 Docker 組建功能，此功能會產生 Docker 影像作為組建輸出。然後，它會將 Docker 映像推送至 Amazon ECR 映像儲存庫。多階段 Docker 影像組建有助於縮小最終 Docker 影像。如需詳細資訊，請參閱[對 Docker 使用多階段組建](https://docs.docker.com/engine/userguide/eng-image/multistage-build/)。

**重要**  
執行此範例可能會導致 AWS 您的帳戶產生費用。這包括 AWS CodeBuild 與 Amazon S3、、 AWS KMS CloudWatch Logs 和 Amazon ECR 相關的 AWS 資源和動作的可能費用。如需詳細資訊，請參閱 [CodeBuild 定價](https://aws.amazon.com/codebuild/pricing)、[Amazon S3 定價](https://aws.amazon.com/s3/pricing)、[AWS Key Management Service 定價](https://aws.amazon.com/kms/pricing)、[Amazon CloudWatch 定價](https://aws.amazon.com/cloudwatch/pricing)和 [Amazon Elastic Container Registry 定價](https://aws.amazon.com/ecr/pricing)。

**Topics**
+ [執行「發佈 Docker 映像到 Amazon ECR」範例](#sample-docker-running)
+ [將 'Publish Docker 映像修改為 Amazon ECR' 範例，以推送至 Docker Hub](sample-docker-docker-hub.md)

## 執行「發佈 Docker 映像到 Amazon ECR」範例
<a name="sample-docker-running"></a>

使用下列程序來執行將 Docker 映像發佈至 Amazon ECR 的範例。如需此範例的詳細資訊，請參閱 [CodeBuild 的「將 Docker 映像發佈至 Amazon ECR 映像儲存庫」範例](#sample-docker)。

**如何執行此範例**

1. 如果您在 Amazon ECR 中已有要使用的映像儲存庫，請跳到步驟 3。否則，如果您使用 使用者而非 AWS 根帳戶或管理員使用者來使用 Amazon ECR，請將此陳述式 （介於 *\$1\$1\$1 BEGIN ADDING STATEMENT HERE \$1\$1\$1* 和 *\$1\$1\$1 END ADDING STATEMENT HERE \$1\$1\$1* 之間） 新增至使用者 （或使用者相關聯的 IAM 群組）。不建議使用 AWS 根帳戶。此陳述式允許建立 Amazon ECR 儲存庫來存放 Docker 映像。省略符號 (`...`) 用於簡化和協助您找到新增陳述式的位置。請不要移除任何陳述式，也不要在政策中輸入這些省略符號。如需詳細資訊，請參閱[《 使用者指南》中的使用內嵌政策 AWS 管理主控台](https://docs.aws.amazon.com/IAM/latest/UserGuide/access_policies_inline-using.html#AddingPermissions_Console)。 **

------
#### [ JSON ]

****  

   ```
   {
       "Version":"2012-10-17",		 	 	 
       "Statement": [
           {
               "Effect": "Allow",
               "Action": [
                   "ecr:CreateRepository"
               ],
               "Resource": "*"
           }
       ]
   }
   ```

------
**注意**  
修改此政策的 IAM 實體必須在 IAM 中具有修改政策的許可。

1. 在 Amazon ECR 中建立映像儲存庫。請務必在建立建置環境和執行建置的相同 AWS 區域中建立儲存庫。如需詳細資訊，請參閱《*Amazon ECR 使用者指南*》中的[建立儲存庫](https://docs.aws.amazon.com/AmazonECR/latest/userguide/repository-create.html)。此儲存庫的名稱必須符合您稍後於此程序中指定的儲存庫名稱 (以 `IMAGE_REPO_NAME` 環境變數表示)。確保 Amazon ECR 儲存庫政策授予 CodeBuild 服務 IAM 角色的映像推送存取權。

1. 將此陳述式 (*\$1\$1\$1 BEGIN ADDING STATEMENT HERE \$1\$1\$1 *和 *\$1\$1\$1 END ADDING STATEMENT HERE \$1\$1\$1* 之間） 新增至您連接至 AWS CodeBuild 服務角色的政策。此陳述式允許 CodeBuild 將 Docker 映像上傳至 Amazon ECR 儲存庫。省略符號 (`...`) 用於簡化和協助您找到新增陳述式的位置。請不要移除任何陳述式，也不要在政策中輸入這些省略符號。

------
#### [ JSON ]

****  

   ```
   {
       "Version":"2012-10-17",		 	 	 
       "Statement": [
           {
               "Effect": "Allow",
               "Action": [
                   "ecr:BatchCheckLayerAvailability",
                   "ecr:CompleteLayerUpload",
                   "ecr:GetAuthorizationToken",
                   "ecr:InitiateLayerUpload",
                   "ecr:PutImage",
                   "ecr:UploadLayerPart"
               ],
               "Resource": "*"
           }
       ]
   }
   ```

------
**注意**  
修改此政策的 IAM 實體必須在 IAM 中具有修改政策的許可。

1. 如本主題的 [目錄結構](#sample-docker-dir)和 [檔案](#sample-docker-files)章節所述建立檔案，然後將其上傳至 S3 輸入儲存貯體或 AWS CodeCommit、GitHub 或 Bitbucket 儲存庫。如需詳細資訊，請參閱*AWS CodePipeline 《 使用者指南*》中的[映像定義檔案參考](https://docs.aws.amazon.com/codepipeline/latest/userguide/file-reference.html)。
**重要**  
請勿上傳 `(root directory name)`，僅上傳 `(root directory name)` 內的檔案即可。  
如果您使用的是 S3 輸入儲存貯體，請務必建立包含這些檔案的 ZIP 檔案，然後將其上傳至輸入儲存貯體。請勿將 `(root directory name)` 新增至 ZIP 檔案，僅新增 `(root directory name)` 內的檔案即可。

1. 建立組建專案、執行組建，以及檢視組建資訊。

    如果您使用主控台來建立您的專案：

   1.  針對 **Operating system (作業系統)**，選擇 **Ubuntu**。

   1.  針對 **Runtime (執行時間)**，選擇 **Standard (標準)**。

   1.  針對**映像**，選擇 **aws/codebuild/standard:5.0**。

   1.  新增下列環境變數：
      +  值為 *region-ID* 的 AWS\$1DEFAULT\$1REGION 
      +  值為 *account-ID* 的 AWS\$1ACCOUNT\$1ID 
      +  值為 Latest 的 IMAGE\$1TAG 
      +  值為 *Amazon-ECR-repo-name* 的 IMAGE\$1REPO\$1NAME 

   如果您使用 AWS CLI 來建立建置專案，`create-project`命令的 JSON 格式輸入可能會與此類似。(以您自己的值取代預留位置。)

   ```
   {
     "name": "sample-docker-project",
     "source": {
       "type": "S3",
       "location": "codebuild-region-ID-account-ID-input-bucket/DockerSample.zip"
     },
     "artifacts": {
       "type": "NO_ARTIFACTS"
     },
     "environment": {
       "type": "LINUX_CONTAINER",
       "image": "aws/codebuild/standard:5.0",
       "computeType": "BUILD_GENERAL1_SMALL",
       "environmentVariables": [
         {
           "name": "AWS_DEFAULT_REGION",
           "value": "region-ID"
         },
         {
           "name": "AWS_ACCOUNT_ID",
           "value": "account-ID"
         },
         {
           "name": "IMAGE_REPO_NAME",
           "value": "Amazon-ECR-repo-name"
         },
         {
           "name": "IMAGE_TAG",
           "value": "latest"
         }
       ],
     },
     "serviceRole": "arn:aws:iam::account-ID:role/role-name",
     "encryptionKey": "arn:aws:kms:region-ID:account-ID:key/key-ID"
   }
   ```

1. 確認 CodeBuild 已成功將 Docker 映像推送至儲存庫：

   1. 在 [https://console.aws.amazon.com/ecr/](https://console.aws.amazon.com/ecr/) 開啟 Amazon ECR 主控台。

   1. 選擇儲存庫名稱。此映像應列在 **Image tag (映像標籤)** 欄中。

### 目錄結構
<a name="sample-docker-dir"></a>

此範例假設此目錄結構。

```
(root directory name)
├── buildspec.yml
└── Dockerfile
```

### 檔案
<a name="sample-docker-files"></a>

此範例使用這些檔案。

`buildspec.yml` (在 `(root directory name)` 中)

```
version: 0.2

phases:
  pre_build:
    commands:
      - echo Logging in to Amazon ECR...
      - aws ecr get-login-password --region $AWS_DEFAULT_REGION | docker login --username AWS --password-stdin $AWS_ACCOUNT_ID.dkr.ecr.$AWS_DEFAULT_REGION.amazonaws.com
  build:
    commands:
      - echo Build started on `date`
      - echo Building the Docker image...          
      - docker build -t $IMAGE_REPO_NAME:$IMAGE_TAG .
      - docker tag $IMAGE_REPO_NAME:$IMAGE_TAG $AWS_ACCOUNT_ID.dkr.ecr.$AWS_DEFAULT_REGION.amazonaws.com/$IMAGE_REPO_NAME:$IMAGE_TAG      
  post_build:
    commands:
      - echo Build completed on `date`
      - echo Pushing the Docker image...
      - docker push $AWS_ACCOUNT_ID.dkr.ecr.$AWS_DEFAULT_REGION.amazonaws.com/$IMAGE_REPO_NAME:$IMAGE_TAG
```

`Dockerfile` (在 `(root directory name)` 中)

```
FROM golang:1.12-alpine AS build
#Install git
RUN apk add --no-cache git
#Get the hello world package from a GitHub repository
RUN go get github.com/golang/example/hello
WORKDIR /go/src/github.com/golang/example/hello
# Build the project and send the output to /bin/HelloWorld 
RUN go build -o /bin/HelloWorld

FROM golang:1.12-alpine
#Copy the build's output binary from the previous build container
COPY --from=build /bin/HelloWorld /bin/HelloWorld
ENTRYPOINT ["/bin/HelloWorld"]
```

**注意**  
CodeBuild 會覆寫自訂 Docker 映像`ENTRYPOINT`的 。

# 將 'Publish Docker 映像修改為 Amazon ECR' 範例，以推送至 Docker Hub
<a name="sample-docker-docker-hub"></a>

若要將「公開 Docker 影像調整為 Amazon ECR」範例，以便將 Docker 影像推送至 Docker Hub，而不是 Amazon ECR，請編輯範例程式碼。如需範例的詳細資訊，請參閱 [CodeBuild 的「將 Docker 映像發佈至 Amazon ECR 映像儲存庫」範例](sample-docker.md)和 [執行「發佈 Docker 映像到 Amazon ECR」範例](sample-docker.md#sample-docker-running)。
**注意**  
如果您使用的是 17.06 之前的 Docker 版本，請移除 `--no-include-email` 選項。

1. 在 `buildspec.yml` 檔案中取代這些 Amazon ECR 特定的程式碼行：

   ```
   ...
     pre_build:
       commands:
         - echo Logging in to Amazon ECR...
         - aws ecr get-login-password --region $AWS_DEFAULT_REGION | docker login --username AWS --password-stdin $AWS_ACCOUNT_ID.dkr.ecr.$AWS_DEFAULT_REGION.amazonaws.com
     build:
       commands:
         - echo Build started on `date`
         - echo Building the Docker image...          
         - docker build -t $IMAGE_REPO_NAME:$IMAGE_TAG .
         - docker tag $IMAGE_REPO_NAME:$IMAGE_TAG $AWS_ACCOUNT_ID.dkr.ecr.$AWS_DEFAULT_REGION.amazonaws.com/$IMAGE_REPO_NAME:$IMAGE_TAG
     post_build:
       commands:
         - echo Build completed on `date`
         - echo Pushing the Docker image...
         - docker push $AWS_ACCOUNT_ID.dkr.ecr.$AWS_DEFAULT_REGION.amazonaws.com/$IMAGE_REPO_NAME:$IMAGE_TAG
   ...
   ```

   換成 Docker Hub 專用的這幾行程式碼：

   ```
   ...
     pre_build:
       commands:
         - echo Logging in to Docker Hub...
         # Type the command to log in to your Docker Hub account here.          
     build:
       commands:
         - echo Build started on `date`
         - echo Building the Docker image...
         - docker build -t $IMAGE_REPO_NAME:$IMAGE_TAG .
         - docker tag $IMAGE_REPO_NAME:$IMAGE_TAG $IMAGE_REPO_NAME:$IMAGE_TAG
     post_build:
       commands:
         - echo Build completed on `date`
         - echo Pushing the Docker image...
         - docker push $IMAGE_REPO_NAME:$IMAGE_TAG
   ...
   ```

1. 將編輯的程式碼上傳至 S3 輸入儲存貯體或 AWS CodeCommit、GitHub 或 Bitbucket 儲存庫。
**重要**  
請勿上傳 `(root directory name)`，僅上傳 `(root directory name)` 內的檔案即可。  
如果您使用的是 S3 輸入儲存貯體，請務必建立包含這些檔案的 ZIP 檔案，然後將其上傳至輸入儲存貯體。請勿將 `(root directory name)` 新增至 ZIP 檔案，僅新增 `(root directory name)` 內的檔案即可。

1. 將 `create-project` 命令中 JSON 格式輸入的這幾行程式碼：

   ```
   ...
       "environmentVariables": [
         {
           "name": "AWS_DEFAULT_REGION",
           "value": "region-ID"
         },
         {
           "name": "AWS_ACCOUNT_ID",
           "value": "account-ID"
         },
         {
           "name": "IMAGE_REPO_NAME",
           "value": "Amazon-ECR-repo-name"
         },
         {
           "name": "IMAGE_TAG",
           "value": "latest"
         }
       ]
   ...
   ```

   換成這幾行程式碼：

   ```
   ...
       "environmentVariables": [
         {
           "name": "IMAGE_REPO_NAME",
           "value": "your-Docker-Hub-repo-name"
         },
         {
           "name": "IMAGE_TAG",
           "value": "latest"
         }
       ]
   ...
   ```

1. 建立建置環境、執行建置，以及檢視相關的建置資訊。

1. 確認 AWS CodeBuild 已成功將 Docker 映像推送至儲存庫。登入 Docker Hub，移至儲存庫，然後選擇 **Tags (標籤)** 索引標籤。`latest` 標籤應該包含最近的 **Last Updated (上次更新)** 值。