LoginSignup
34
33

More than 1 year has passed since last update.

【AWS】ECS構築の基礎 −CI/CD編 (CodeCommit/CodeBuild/CodePipeline)−

Last updated at Posted at 2021-07-10

はじめに

ECSとECRを触れるようになったので、今回はCodeCommit, CodeBuild, CodePipelineを使って、AWSサービスのみでCI/CDパイプラインを構築してみました。

GitHub ActionsによるCI/CDパイプラインの構築については以前記事を書きました。
もし興味があればこちらをご覧ください。

AWSのCI/CD関連サービス

CI(Continuous Integration)では、ソースコードをホスティングサービス(GitHub, Bitbucketなど)にプッシュしたときに、自動でテスト(ビルド)サーバ(GitHub Actions, Jenkins CI, Circle CIなど)でテストを行い、ビルドの成功可否を開発者にフィードバックします。
CIを行うことで早期にバグを発見することができるようになります。
CodeCommitはホスティングサービスの役割、CodeBuildはテストサーバの役割をもつAWSサービスです。

また、CD(Continuous Delivery)はCIを拡張した手法で、ビルドやテストだけでなく、リリースプロセス全体を自動化します。
CDでは、ビルドとテストを実行した後、テスト環境またはステージング環境にデプロイして、システムテストやUIテストを行います。
開発者は、これらのテストが完了した後に、最後のステップとして本番(運用)環境への更新を承認します。

CDを行うことでリリースサイクルを早め、市場からのフィードバックをすぐにソフトウェアへ反映させることができるようになります。
CodeDeployはデプロイを自動化する役割をもつAWSサービスで、ECSのblue/greenデプロイ(古いサーバを残したまま新しいサーバを構築し、一定期間経過後に新しいサーバが安定したのを確認してから古いサーバを消去するデプロイ手法)などに使用します。

CI/CDの流れと使用するサービスをまとめると以下の図のようになります。
CodePipelineでCI/CD全体のステップを管理することができます。

CodeCommit

以下でCodeCommitの操作を学びます。

  1. CodeCommitにリポジトリを作成し、ローカルにクローンを作成
  2. GitHubのコードをローカルにプルして、1で作成したクローンにコードを追加
  3. コードをCodeCommitにプッシュ

実装

CodeCommitを開いて"リポジトリを作成"を選択すると以下の画面になります。
リポジトリ名と説明(任意)を記述すれば作成完了です。
スクリーンショット 2021-07-08 21.55.08.png

以下の画面になるので、接続のステップを順番に実行していきます。
スクリーンショット 2021-07-08 22.09.37.png

まず、brew install gitでGitクライアントをインストールします。

次にGit認証情報を作成します。
ログイン中のIAMユーザecs-courseにCodeCommitへのアクセス権限を付加します。
スクリーンショット 2021-07-08 22.13.10.png

AWSCodeCommitPowerUserを付加します。
スクリーンショット 2021-07-08 22.14.51.png

認証情報タブからAWS CodeCommitリポジトリへのHTTPS接続の認証に使用できるユーザー名とパスワードを生成します。
スクリーンショット 2021-07-08 22.16.32.png
スクリーンショット 2021-07-08 22.17.32.png

git clone ~でリポジトリsimplehttpのクローンをローカルに作成します。
git remote -vを実行すると、リモートリポジトリがCodeCommitにあることが確認できます。

origin  https://git-codecommit.ap-northeast-1.amazonaws.com/v1/repos/simplehttp (fetch)
origin  https://git-codecommit.ap-northeast-1.amazonaws.com/v1/repos/simplehttp (push)

cd simplehttpでディレクトリを移動し、git clone https://github.com/gkoenig/go-simplehttp.git /tmp/simplehttpでGitHubからリポジトリをクローンします。
cp /tmp/simplehttp/Dockerfile /tmp/simplehttp/README.md /tmp/simplehttp/simpleHTTP.go .simplehttpにファイルをコピーします。

コミットとプッシュを行います。

$ git add .
$ git commit -m 'initial commit'
$ git push

コンソールからsimplehttpを開くと、正常にプッシュされたことを確認できます。
スクリーンショット 2021-07-08 22.47.17.png

CodeBuild

以下でCodeBuildの操作を学びます。

  1. IAMロールの作成
  2. ビルドプロジェクトの作成

実装

一つの手順が長いので項目をわけます。

IAMロールの作成

CloudWatchLogsやCodeCommitへのアクセスに関するIAMポリシーを新しく作成します。
スクリーンショット 2021-07-09 21.13.11.png

{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Sid": "CloudWatchLogsPolicy",
      "Effect": "Allow",
      "Action": [
        "logs:CreateLogGroup",
        "logs:CreateLogStream",
        "logs:PutLogEvents"
      ],
      "Resource": [
        "*"
      ]
    },
    {
      "Sid": "CodeCommitPolicy",
      "Effect": "Allow",
      "Action": [
        "codecommit:GitPull"
      ],
      "Resource": [
        "*"
      ]
    },
    {
      "Sid": "S3GetObjectPolicy",
      "Effect": "Allow",
      "Action": [
        "s3:GetObject",
        "s3:GetObjectVersion"
      ],
      "Resource": [
        "*"
      ]
    },
    {
      "Sid": "S3PutObjectPolicy",
      "Effect": "Allow",
      "Action": [
        "s3:PutObject"
      ],
      "Resource": [
        "*"
      ]
    },
    {
      "Sid": "ECRPullPolicy",
      "Effect": "Allow",
      "Action": [
        "ecr:BatchCheckLayerAvailability",
        "ecr:GetDownloadUrlForLayer",
        "ecr:BatchGetImage",
        "ecr:PutImage",
        "ecr:InitiateLayerUpload",
        "ecr:UploadLayerPart",
        "ecr:CompleteLayerUpload"
      ],
      "Resource": [
        "*"
      ]
    },
    {
      "Sid": "ECRAuthPolicy",
      "Effect": "Allow",
      "Action": [
        "ecr:GetAuthorizationToken"
      ],
      "Resource": [
        "*"
      ]
    },
    {
      "Sid": "S3BucketIdentity",
      "Effect": "Allow",
      "Action": [
        "s3:GetBucketAcl",
        "s3:GetBucketLocation"
      ],
      "Resource": 
        "*"
    }
  ]
}

ポリシー名はCodeBuildServiceRolePolicyとします。
スクリーンショット 2021-07-09 21.15.42.png

次にIAMロールを作成します。
CodeBuildというユースケースを選択します。
スクリーンショット 2021-07-09 21.17.35.png

作成したポリシーをアタッチします。
スクリーンショット 2021-07-09 21.18.45.png

ロール名はCodeBuildServiceRoleとします。
スクリーンショット 2021-07-09 21.28.03.png

ポリシーをもう一つアタッチします。
スクリーンショット 2021-07-09 21.31.55.png

AmazonElasticContainerRegistryPublicPowerUserを選択します。
スクリーンショット 2021-07-09 21.32.38.png

ビルドプロジェクトの作成

CodeBuildの画面からビルドプロジェクトを新しく作成します。
スクリーンショット 2021-07-09 21.59.35.png
スクリーンショット 2021-07-09 21.59.51.png
スクリーンショット 2021-07-09 22.00.19.png
スクリーンショット 2021-07-09 22.01.00.png
スクリーンショット 2021-07-09 22.01.15.png

Buildspecの設定の部分でbuildspecファイルを使用するを選択する場合は、ソースコードのルートディレクトリにbuildspec.ymlが必要となります。
buildspec.ymlには以下のように、buildコマンドを記述します。
<<account-id>>にはアカウントIDを記述します。

buildspec.yml
version: 0.2

phases:
  pre_build:
    commands:
      - echo Logging in to Amazon ECR...
      - aws --version
      - echo $AWS_DEFAULT_REGION
      - $(aws ecr get-login --region $AWS_DEFAULT_REGION --no-include-email)
      - REPOSITORY_URI=<<account-id>>.dkr.ecr.ap-northeast-1.amazonaws.com/ecr-simplehttp
      - COMMIT_HASH=$(echo $CODEBUILD_RESOLVED_SOURCE_VERSION | cut -c 1-7)
      - IMAGE_TAG=${COMMIT_HASH:=latest}
  build:
    commands:
      - echo Build started on `date`
      - echo Building the Docker image...
      - docker build -t $REPOSITORY_URI:latest .
      - docker tag $REPOSITORY_URI:latest $REPOSITORY_URI:$IMAGE_TAG
  post_build:
      commands:
        - echo Build completed on `date`
        - docker push $REPOSITORY_URI:latest
        - docker push $REPOSITORY_URI:$IMAGE_TAG

ビルドプロジェクトを作成できたら、ビルドを開始します。
すべて成功すればOKです。
スクリーンショット 2021-07-10 8.31.25.png

ECRのリポジトリ画面からもイメージがプッシュされたことを確認できます。
スクリーンショット 2021-07-10 8.48.26.png

CodePipeline

CodePipelineを使って、CI/CDパイプラインを構築します。

  1. アーティファクト作成のためにbuildspec.ymlを更新
  2. パイプラインの構築
    1. CodeCommitリポジトリとの連携
    2. CodeBuildのビルドプロジェクトとの連携
    3. デプロイプロバイダとしてECSを設定

実装

ビルドやテストのプロセスをアーティファクトimagedefinitions.jsonとして出力するために、buildspec.ymlに以下の記述を加えてプッシュします。

        - printf '[{"name":"simplehttp-container","imageUri":"%s"}]' $REPOSITORY_URI:$IMAGE_TAG > imagedefinitions.json
  artifacts:
      files: imagedefinitions.json

CodePipelineから新規のパイプラインを作成します。
スクリーンショット 2021-07-10 9.20.44.png

ソースコードのリポジトリ(CodeCommit)との連携を設定します。
スクリーンショット 2021-07-10 9.22.46.png

ビルドプロジェクトとの連携を設定します。
スクリーンショット 2021-07-10 9.24.29.png

デプロイプロバイダにAmazon ECSを選択し、クラスターやサービスは前の記事で作成したものを選択します。
デプロイプロバイダをAmazon ECSにすることで、リポジトリのコードを変更したとき、パイプラインが新しいDockerイメージを作成してコンテナレジストリにプッシュし、更新されたイメージをECSにデプロイします。
スクリーンショット 2021-07-10 9.38.39.png

パイプラインを作成すると実行を開始し、以下の画面になれば成功です。
スクリーンショット 2021-07-10 10.01.33.png

参考資料

34
33
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
34
33