紙一重の積み重ね

アラフォーのエンジニアがなれる最高の自分を目指して、学んだことをこつこつ情報発信するブログです。

GitHub Actions で AWS ECS に自動でプロイする CI/CD 環境を構築する #Qiita #aws

はじめに

この記事は Qiita AWS ADVENT Calendar 2022 の22日目の記事です。 今回、GitHub Actions を使って、ECS の自動デプロイを試みたので記事にします。

環境

  • OS
    • Ubuntu
  • コンテナ管理サービス
    • AWS ECS fargate
  • コンテナレジストリ
    • AWS ECR
  • GitHub Actions

やりたいこと

  • 手動で ECS にコンテナイメージをデプロイしたくない
  • develop ブランチなど、特定のブランチが更新されたタイミングで自動的に AWS ECS にデプロイしてほしい

実現方法

  • GitHub Actions で ECS に自動でプロイする

やってみた

name: sample-ecs-deploy

on:
  push:
    # 任意のブランチ
    branches:
      - hoge_branch

jobs:
  sample-deploy:
    runs-on: ubuntu-latest
    env:
      SAMPLE_IMAGE_NAME: ${{ secrets.SAMPLE_ECR_REPOSITORY }}
    steps:
      - name: Checkout
        uses: actions/checkout@v3

      - name: Set up Docker Buildx
        uses: docker/setup-buildx-action@v2

      - name: Configure AWS credentials (sample)
        uses: aws-actions/configure-aws-credentials@v1
        with:
          aws-access-key-id: ${{ secrets.SAMPLE_AWS_ACCESS_KEY_ID }}
          aws-secret-access-key: ${{ secrets.SAMPLE_AWS_SECRET_ACCESS_KEY }}
          aws-region: ${{ secrets.SAMPLE_AWS_REGION }}

      - name: Login to Amazon ECR (sample)
        id: login-ecr-sample
        uses: aws-actions/amazon-ecr-login@v1

      - name: Build and push sample image (sample)
        uses: docker/build-push-action@v3
        with:
          push: true
          context: ./sample
          tags: ${{ steps.login-ecr-sample.outputs.registry }}/${{ env.SAMPLE_IMAGE_NAME }}:${{ github.sha }}
          cache-from: type=gha,scope=sample
          cache-to: type=gha,scope=sample,mode=max

      - name: Download task definition
        run: aws ecs describe-task-definition --task-definition sample-app-sample --query taskDefinition > task-definition.json

      - name: Fill in the new image ID in the Amazon ECS task definition
        id: task-def
        uses: aws-actions/amazon-ecs-render-task-definition@v1
        with:
          task-definition: task-definition.json
          container-name: sample-app-container-sample
          image: ${{ steps.login-ecr-sample.outputs.registry }}/${{ env.SAMPLE_IMAGE_NAME }}:${{ github.sha }}

      - name: Deploy Amazon ECS task definition
        uses: aws-actions/amazon-ecs-deploy-task-definition@v1
        with:
          task-definition: ${{ steps.task-def.outputs.task-definition }}
          service: sample-app-service-sample
          cluster: sample-app-cluster

GitHub Secrets の設定

    env:
      SAMPLE_IMAGE_NAME: ${{ secrets.SAMPLE_ECR_REPOSITORY }}

GitHub Secrets からシークレット値を取得している。 ECRのリポジトリを設定する。

Github のヘッダーメニューから Settings をクリックする。

Secrets メニューの Actions をクリックする。

New repository secret をクリックして、ECRのリポジトリを設定する。

GitHub Actions で別リポジトリを clone する

    steps:
      - name: Checkout
        uses: actions/checkout@v3

AWS 認証情報の設定

GitHub - aws-actions/configure-aws-credentials: Configure AWS credential environment variables for use in other GitHub Actions.

から、GitHub Actions で使用するために、AWS 認証情報とリージョン環境変数を設定する。 secrets の値は、GitHub のシークレット値を使用する。

      - name: Configure AWS credentials (sample)
        uses: aws-actions/configure-aws-credentials@v1
        with:
          aws-access-key-id: ${{ secrets.SAMPLE_AWS_ACCESS_KEY_ID }}
          aws-secret-access-key: ${{ secrets.SAMPLE_AWS_SECRET_ACCESS_KEY }}
          aws-region: ${{ secrets.SAMPLE_AWS_REGION }}

ECR へログイン

      - name: Login to Amazon ECR (sample)
        id: login-ecr-sample
        uses: aws-actions/amazon-ecr-login@v1

ECR へイメージをプッシュする

github.sha で、GitHub からコミットハッシュを取得し、コンテナイメージのタグとして設定する。

      - name: Build and push sample image (sample)
        uses: docker/build-push-action@v3
        with:
          push: true
          context: ./sample
          tags: ${{ steps.login-ecr-sample.outputs.registry }}/${{ env.SAMPLE_IMAGE_NAME }}:${{ github.sha }}
          cache-from: type=gha,scope=sample
          cache-to: type=gha,scope=sample,mode=max

ECS のタスク定義を出力

JSON形式で出力する。

      - name: Download task definition
        run: aws ecs describe-task-definition --task-definition sample-app-sample --query taskDefinition > task-definition.json

ECS のタスク定義にコンテナイメージを紐づけ

GitHub - aws-actions/amazon-ecs-render-task-definition: Inserts a container image URI into an Amazon ECS task definition JSON file. を使って、タスク定義の コンテナイメージを、先程 push した イメージのURIに書き換える。

      - name: Fill in the new image ID in the Amazon ECS task definition
        id: task-def
        uses: aws-actions/amazon-ecs-render-task-definition@v1
        with:
          task-definition: task-definition.json
          container-name: sample-app-container-sample
          image: ${{ steps.login-ecr-sample.outputs.registry }}/${{ env.SAMPLE_IMAGE_NAME }}:${{ github.sha }}

ECS にタスク定義を反映

GitHub - aws-actions/amazon-ecs-deploy-task-definition: Registers an Amazon ECS task definition and deploys it to an ECS service. を使って、変更したタスク定義を ECS のサービスとクラスターにデプロイする。

      - name: Deploy Amazon ECS task definition
        uses: aws-actions/amazon-ecs-deploy-task-definition@v1
        with:
          task-definition: ${{ steps.task-def.outputs.task-definition }}
          service: sample-app-service-sample
          cluster: sample-app-cluster

まとめ

GitHub Actions を使うことで開発者体験がめちゃめちゃ上がりました。来年も、開発者体験を上げる仕組みをどんどん作っていきたいと思います。

明日のアドベントカレンダーは、 saba_can00 - Qiita さんです!