AWS CodePipeline と CodeBuild でアップロードから自動デプロイする
記事の「実践」を 1 項目ずつ進めるためのページです。AWS マネジメントコンソールで操作したら、右の一覧にチェックを入れてください。チェックはこのブラウザに保存されます。
準備 9 項目中 1 番目
前提条件
- リージョン:
ap-northeast-1(東京) - AWS マネジメントコンソールにログイン済みであること
- S3・CodePipeline・CodeBuild の操作と、IAM ロール(CodePipeline・CodeBuild のサービスロール)の作成ができる権限があること
- AWS CloudShell が使えること
S3 のバケットとオブジェクトの基本は「Amazon S3 でバケットを作成しオブジェクトを管理する」で解説しています。
準備 9 項目中 2 番目
作成するリソース一覧
S3 のバケット名は全世界で一意にする必要があるため、名前の末尾に自分の AWS アカウント ID(12 桁)を付けます。以降の <アカウントID> は自分のアカウント ID に置き換えてください。
| リソース種別 | リソース名 | 用途 |
|---|---|---|
| S3 バケット | cicd-handson-source-<アカウントID> | ソースの zip(site.zip)を置くバケット。バージョニングを有効にする |
| S3 バケット | cicd-handson-deploy-<アカウントID> | ビルド成果物を展開するデプロイ先のバケット(非公開) |
| CodeBuild プロジェクト | cicd-handson-build | buildspec.yml に従って index.html を生成する |
| CodePipeline パイプライン | cicd-handson-pipeline | Source → Build → Deploy の 3 ステージ |
| IAM ロール | CodePipeline・CodeBuild のサービスロール | パイプライン・ビルドプロジェクトの作成時にコンソールが自動で作成する |
| その他 | アーティファクトストア用の S3 バケット、EventBridge ルール、CloudTrail 証跡 | パイプラインの作成時にコンソールが自動で設定する |
手順 9 項目中 3 番目
ステップ1: ソース用とデプロイ先の S3 バケットを作成する
- AWS マネジメントコンソールにログインし、リージョンが
ap-northeast-1(東京)であることを確認します - 画面右上のアカウント名をクリックし、表示されたアカウント ID(12 桁)を控えます
- 上部の検索バーに
S3と入力し、表示された「S3」を選択します - 左側ナビゲーションの「汎用バケット」を選択し、「バケットを作成」をクリックします
- 以下を設定します
- バケット名前空間:
グローバル名前空間(デフォルトのまま) - バケット名:
cicd-handson-source-<アカウントID> - このバケットのブロックパブリックアクセス設定: 「パブリックアクセスをすべてブロック」にチェックが入ったまま
- バケットのバージョニング:
有効にする
- バケット名前空間:
- その他の項目はデフォルトのままにし、ページ下部の「バケットを作成」をクリックします
- もう一度「バケットを作成」をクリックし、以下を設定します
- バケット名前空間:
グローバル名前空間(デフォルトのまま) - バケット名:
cicd-handson-deploy-<アカウントID> - このバケットのブロックパブリックアクセス設定: 「パブリックアクセスをすべてブロック」にチェックが入ったまま
- バケットのバージョニング: デフォルト(
無効にする)のまま
- バケット名前空間:
- その他の項目はデフォルトのままにし、「バケットを作成」をクリックします
- バケット一覧に 2 つのバケットが表示されることを確認します
手順 9 項目中 4 番目
ステップ2: CloudShell でソースの zip を作成してアップロードする
- コンソール上部のツールバーにある CloudShell のアイコンをクリックし、CloudShell を起動します(リージョンが
ap-northeast-1のままであることを確認します) - アカウント ID とバケット名を変数に入れます
ACCOUNT_ID=$(aws sts get-caller-identity --query Account --output text)
SRC_BUCKET=cicd-handson-source-${ACCOUNT_ID}
DEPLOY_BUCKET=cicd-handson-deploy-${ACCOUNT_ID}
echo ${SRC_BUCKET} ${DEPLOY_BUCKET}
- 作業用のディレクトリを作り、ビルドの手順書
buildspec.ymlを作成します。buildフェーズでsrc/index.htmlの目印(__BUILD_NUMBER__と__BUILD_TIME__)をビルド番号とビルド日時(UTC)に置き換えてdist/index.htmlに出力し、artifactsでdistの中身を成果物にします
mkdir -p ~/cicd-handson/src && cd ~/cicd-handson
cat > buildspec.yml <<'EOF'
version: 0.2
phases:
build:
commands:
- echo "Build number ${CODEBUILD_BUILD_NUMBER}"
- mkdir -p dist
- BUILD_TIME=$(date -u '+%Y-%m-%d %H:%M:%S')
- sed -e "s/__BUILD_NUMBER__/${CODEBUILD_BUILD_NUMBER}/" -e "s/__BUILD_TIME__/${BUILD_TIME}/" src/index.html > dist/index.html
- cat dist/index.html
artifacts:
base-directory: dist
files:
- '**/*'
EOF
- 元になる
src/index.htmlを作成します
cat > src/index.html <<'EOF'
<!DOCTYPE html>
<html lang="ja">
<head><meta charset="UTF-8"><title>CI/CD Handson</title></head>
<body>
<h1>Hello CodePipeline v1</h1>
<p>Build number: __BUILD_NUMBER__</p>
<p>Built at (UTC): __BUILD_TIME__</p>
</body>
</html>
EOF
- 2 つのファイルを
site.zipにまとめます。buildspec.ymlが zip のルートに来るように、作業ディレクトリの中で zip を作ります
zip -r site.zip buildspec.yml src
unzip -l site.zip
unzip -lの結果にbuildspec.ymlとsrc/index.htmlが表示されることを確認し、ソース用バケットにアップロードします
aws s3 cp site.zip s3://${SRC_BUCKET}/site.zip
手順 9 項目中 5 番目
ステップ3: パイプラインを作成する(パイプラインの設定とソースステージ)
- 上部の検索バーに
CodePipelineと入力し、表示された「CodePipeline」を選択します - 「パイプラインを作成する」をクリックします
- 「Step 1: 作成オプションを選択する」で「カスタムパイプラインを構築する」を選択し、「次に」をクリックします
- 「Step 2: パイプラインの設定を選択する」で以下を設定し、「次に」をクリックします
- パイプライン名:
cicd-handson-pipeline - サービスロール:
新しいサービスロール(ロール名は自動で入力されたままにします) - その他の項目はデフォルトのままにします(実行モードは既定の
キュー)。パイプラインタイプを選ぶ項目は無く、V2 のパイプラインとして作成されます
- パイプライン名:
- 「Step 3: ソースステージを追加」で以下を設定します
- ソースプロバイダー:
Amazon S3 - バケット: 入力欄をクリックし、候補から
cicd-handson-source-<アカウントID>を選択します - S3 オブジェクトキー:
site.zip - 「ソースの変更を自動的に検出する EventBridge ルールを作成」: チェックが入ったまま(
site.zipの更新を EventBridge ルールで検知してパイプラインを起動します) - 「ステージ障害時の自動再試行を有効にする」はデフォルトのままにします
- ソースプロバイダー:
- 「次に」をクリックします
手順 9 項目中 6 番目
ステップ4: ビルドステージで CodeBuild プロジェクトを作成する
- 「Step 4: ビルドステージを追加する」で、ビルドプロバイダーの「その他のビルドプロバイダー」を選択し、
AWS CodeBuildを選びます(既定の「コマンド」は、CodeBuild のプロジェクトを作らずにパイプラインの中でコマンドを実行する方式です。今回は buildspec.yml を使うので CodeBuild を選びます) - リージョンが
アジアパシフィック (東京)であることを確認し、「プロジェクト名」の横の「プロジェクトを作成する」をクリックします - 別ウィンドウで CodeBuild のプロジェクト作成画面が開くので、以下を設定します
- プロジェクト名:
cicd-handson-build - 環境イメージ:
マネージド型イメージ(オペレーティングシステムやイメージなど、環境のその他の項目はデフォルトのまま) - サービスロール:
新しいサービスロール(ロール名は自動で入力されたまま) - ビルド仕様:
buildspec ファイルを使用する(Buildspec 名は空欄のまま。ソースのルートにあるbuildspec.ymlが使われます) - その他の項目はデフォルトのままにします
- プロジェクト名:
- 画面下部の「CodePipeline に進む」をクリックします。ウィンドウが閉じ、パイプラインの作成画面に「プロジェクト名」として
cicd-handson-buildが入ります - その他の項目(ビルドタイプ
単一ビルド、入力アーティファクトSourceArtifact)はデフォルトのままにし、「次に」をクリックします - 「Step 5: テストステージを追加」は「テストステージをスキップ」をクリックします(確認ダイアログが表示された場合は「スキップ」をクリックします)
手順 9 項目中 7 番目
ステップ5: デプロイステージを設定してパイプラインを作成する
- 「Step 6: デプロイステージを追加する」で以下を設定します
- デプロイプロバイダー:
Amazon S3 - リージョン:
アジアパシフィック (東京) - 入力アーティファクト:
BuildArtifact(自動で入っています) - バケット: 入力欄をクリックし、候補から
cicd-handson-deploy-<アカウントID>を選択します - デプロイパス - オプショナル: 空欄のまま(バケットのルートに展開されます)
- 「デプロイする前にファイルを抽出する」: チェックを入れる(ビルドの成果物は zip でアーティファクトストアに保存されているため、展開してからデプロイ先に置きます)
- 「ステージ障害時の自動ロールバックを設定」はデフォルトのままにします
- デプロイプロバイダー:
- 「次に」をクリックします
- 「Step 7: レビュー」で設定内容を確認し(パイプラインタイプが
V2になっています)、「パイプラインを作成する」をクリックします
手順 9 項目中 8 番目
ステップ6: 実行結果と展開されたファイルを確認する
パイプラインを作成すると、ソース用バケットにある site.zip を使って最初の実行が自動で始まります。
- パイプラインの詳細画面で、Source → Build → Deploy の順に各ステージが進むのを待ちます(数分かかることがあります)
- 3 つのステージがすべて「すべてのアクションが成功しました。」になったことを確認します
- Build ステージのアクションの「詳細を表示」をクリックし、ビルドログに
buildspec.ymlのcat dist/index.htmlの出力(ビルド番号と日時が入った HTML)が表示されていることを確認します - CloudShell に戻り、デプロイ先のバケットに展開された
index.htmlの中身を表示します
aws s3 ls s3://${DEPLOY_BUCKET}/
aws s3 cp s3://${DEPLOY_BUCKET}/index.html -
Hello CodePipeline v1 の見出しと、__BUILD_NUMBER__ が 1 に、__BUILD_TIME__ がビルドした日時に置き換わった HTML が表示されれば、S3 に置いた zip が CodeBuild でビルドされ、デプロイ先のバケットに展開されたことが確認できます。
手順 9 項目中 9 番目
ステップ7: zip を更新して自動で再実行されることを確認する
- CloudShell で
src/index.htmlの見出しをv2に書き換え、zip を作り直してアップロードします
cd ~/cicd-handson
sed -i 's/Hello CodePipeline v1/Hello CodePipeline v2/' src/index.html
rm site.zip
zip -r site.zip buildspec.yml src
aws s3 cp site.zip s3://${SRC_BUCKET}/site.zip
- CodePipeline のコンソールに戻り、パイプライン
cicd-handson-pipelineの詳細画面を開きます。手動で「変更をリリースする」をクリックしなくても、新しい実行が始まることを確認します(始まるまで少し時間がかかることがあります) - 上部の「実行」タブ(または左側ナビゲーションの「履歴」)を選択して「実行履歴」を開き、2 つ目の実行のステータスが「成功しました」になったことを確認します。トリガーが
CloudWatchEvent(EventBridge ルール)になっていて、zip のアップロードで自動的に始まったことが分かります。「ソースリビジョン」には S3 オブジェクトのバージョン ID が記録されています
- CloudShell で、デプロイ先の
index.htmlを再度表示します
aws s3 cp s3://${DEPLOY_BUCKET}/index.html -
見出しが Hello CodePipeline v2、ビルド番号が 2 に変わっていれば、ソースの更新をきっかけにパイプラインが自動で再実行され、新しい成果物がデプロイされたことが確認できます。