☁️

【小ネタ】AWS CDKで定義したリソースをGitHub Actions経由でデプロイする際の設定の流れ

2023/08/09に公開

※ メモ目的で書いたため、あまり丁寧に書いていません。

前提として、ローカルからcdk deployをしリソースが手動でデプロイできることを想定しています。

1. GitHubと連携するためにOIDCロールを作成

1-1 新しいプロバイダの設定

GitHub Actions のIDトークンを使ってAWSリソースにアクセスするを参考に新規のプロバイダの設定をする。

プロバイダの URL: token.actions.githubusercontent.com
Audience(ClientID): 対象のGitHub RepositoryのURL

別途Audience(ClientID)に関しては、sts.amazonaws.comを追加しておく。(参考)

1-2 ポリシーの作成

後述する1-3のOIDCロールを作成にて付与するためのポリシーを作成。

今回は以下のように設定。

最小権限を意識するならもっと削れるはず。

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Action": [
                "s3:getBucketLocation",
                "s3:List*",
                "cloudformation:CreateStack",
                "cloudformation:CreateChangeSet",
                "cloudformation:DeleteChangeSet",
                "cloudformation:DescribeChangeSet",
                "cloudformation:DescribeStacks",
                "cloudformation:DescribeStackEvents",
                "cloudformation:ExecuteChangeSet",
                "cloudformation:GetTemplate"
            ],
            "Resource": [
                "arn:aws:s3:::*",
                "arn:aws:cloudformation:<your region>:<your acount>:stack/CDKToolkit/*",
                "arn:aws:cloudformation:<your region>:<your acount>:stack/*/*"
            ],
            "Effect": "Allow"
        },
        {
            "Action": [
                "s3:PutObject",
                "s3:GetObject"
            ],
            "Resource": "arn:aws:s3:::cdk-*-assets-<your acount>-<your region>/*",
            "Effect": "Allow"
        },
        {
            "Action": "ecr:*",
            "Resource": "arn:aws:ecr:ap-northeast-1:<your acount>:repository/*",
            "Effect": "Allow"
        },
        {
            "Action": "ecr:GetAuthorizationToken",
            "Resource": "*",
            "Effect": "Allow"
        },
        {
            "Action": "ssm:GetParameter",
            "Resource": "arn:aws:ssm:ap-northeast-1:<your acount>:parameter/cdk-bootstrap/*/version",
            "Effect": "Allow"
        },
        {
            "Action": "iam:PassRole",
            "Resource": "arn:aws:iam::<your acount>:role/cdk-*-cfn-exec-role-<your acount>-<your region>",
            "Effect": "Allow"
        },
        {
            "Effect": "Allow",
            "Action": "route53:ListHostedZonesByName",
            "Resource": "*"
        }
    ]
}

1-3 OIDCロールを作成

ロールの追加を選択し、Webアイデンティティを選択。

その後、先ほど作成したプロバイダとAudienceを選択。

ロールを作成。

作成後にやること

このままGithub Actionsのワークフローを作成し実行すると"Not authorized to perform sts:AssumeRoleWithWebIdentity"というエラーが発生する。

【小ネタ】GitHub Actions用のIAMロールをAWSマネジメントコンソールから作成する際の注意点を参考にしながら作成したロールの信頼関係を編集する。

作成したロールの詳細から「信頼関係」にいき、"Condition"の項目を以下のような形で変更。

  "Action": "sts:AssumeRoleWithWebIdentity",
  "Condition": {
    "StringLike": {
      "token.actions.githubusercontent.com:sub": "repo:${GitHubOrg}/${RepositoryName}:*"
    }
  }

筆者に関してはrepo:${GitHubOrg}/${RepositoryName}:*の部分は、具体的なrepository名を指定した。

2.Github Actionsのワークフローを作成

CDKのコードが配置されているリポジトリのワークフローにyamlを追加。

以下はdev環境用に筆者が書いたもの。

name: Deploy Cdk

on:
  push:
    branches:
      - dev

env:
  AWS_OIDC_ROLE_ARN: <your role arn>
  AWS_REGION:<your region>

jobs:
  deploy_cdk:
    runs-on: ubuntu-latest
    defaults:
      run:
        working-directory: cdk
    permissions:
      id-token: write
      contents: read
    steps:
      - name: Checkout
        uses: actions/checkout@v3
      - name: Set using var
        id: set-var
        run: |
          ROLE=${{ env.AWS_OIDC_ROLE_ARN }}
          DEPLOY_CMD="npx cdk deploy -c stage=dev"
          echo "deploy_role=$ROLE" >> $GITHUB_OUTPUT
          echo "deploy_cmd=$DEPLOY_CMD" >> $GITHUB_OUTPUT
      - name: Assume Role
        uses: aws-actions/configure-aws-credentials@v1
        with:
          role-to-assume: ${{ steps.set-var.outputs.deploy_role }}
          aws-region: ${{env.AWS_REGION}}
      - name: Cache CDK Dependency
        uses: actions/cache@v3
        id: cache_cdk_dependency_id
        env:
          cache-name: cache-cdk-dependency
        with:
          path: ./cdk/node_modules
          key: ${{ runner.os }}-build-${{ env.cache-name }}-${{ hashFiles('package-lock.json') }}

      - name: Install dependencies
        run: npm install

      - name: CDK Deploy
        run: |
          ${{ steps.set-var.outputs.deploy_cmd }}

3. Github Actionsのワークフロー実行

上の例の場合では、devブランチにpushしアクションが起動。

その後、正常にデプロイされることを確認。

おしまい。

Discussion