DevOps/SRE に興味がある&AWS DVA の資格取得を目指しているのですが、インフラ(特にネットワーク)の業務経験しかない自分にとってCI/CD?何それ?状態でイメージすらつかない状態でした。
じゃあ実際にやってみよう!そうすれば少しは理解できるかも!という事で、今回 AWS Hands-on for Beginners シリーズにある CI/CD 構築をやってみました。
このハンズオンで学んだこと
実際にこのハンズオンをやってみて理解できたこと、実践できたことは以下です。
・CodeCommit, CodeBuild, CodeDeploy, CodePipeline の基本と特徴の理解
・AWS Code サービス群を利用したCI/CDパイプラインの構築
特にコミット・ビルド・デプロイ・パイプライン それぞれの違いや役割を理解できたことは、今回のハンズオンを実践していく中で自分の頭の中にイメージが構築されていく感じを実感できました。
(このコースの終わりにも紹介されていますが)Auto Scaling されるコンピューティングリソースに対して CI/CD 環境を構築するにはどうすれば良いのだろうか?ともう少し踏み込んだ構成に自分のイメージの範囲を広げることができるようになった事も大きいと思います。
利用サービスについて
今回のハンズオンで利用したサービスは以下です。
AWS Code サービス群
・CodeCommit
- フルマネージド型のソース管理サービス
- 既存のGit ツールともシームレスに連携可能
- 月々のアクティブユーザー数、APIリクエスト数、利用容量による課金体系
・CodeBuild
- ソースコードをコンパイル・テスト実行し、デプロイ可能なソフトウェアパッケージを作成できるフルマネージド型のビルドサービス
- 利用した分数のみ支払う
・CodeDeploy
- 様々なコンピューティングリソースに対してデプロイ可能
- Auto Scaling する構成に対しても連動して自動でデプロイ可能
- AWS 上のリソースを対象としたデプロイの場合、料金は発生しない
・CodePipeline
- フルマネージド型の継続的デリバリーサービス
- ソースコードの変更をトリガーとし、ビルド・デプロイ一連の流れを自動的に実行
- アクティブなパイプライン数によって料金が決まる
構成について
今回実践した環境構築は以下です。
上半分と下半分で利用するサービスが異なりますが、どちらにも共通している事は、Cloud9 から CodeCommit に対して[git push]すると CodePipeline が変更を検知し、自動でデプロイまで実行してくれる点です。
対して異なる点は、利用するサービスが違うという事からデプロイする目的が異なります。
上半分はデプロイ先が S3バケットであるためファイルのアップロードを目的としていますが、下半分はデプロイ先が EC2インスタンスであるため、ソースコードからソフトウェアパッケージを作成し対象のリソースへデプロイおよびソースコードの変更を検知すると自動でデプロイをさせることが目的となっています。
構築時のポイント
ここからは個人的に「ここは大事なポイントだな」と思ったポイントについて紹介します。
その1
最終的に EC2インスタンスへのデプロイを自動化させるにあたって、CodeDeploy のエージェントをインストールする必要がありますので、以下を参考に CodeDeploy エージェントをインストールしました。
実行したコマンドは以下です。
sudo yum update
sudo yum install ruby
sudo yum install wget
cd /home/ec2-user
wget https://aws-codedeploy-ap-northeast-1.s3.ap-northeast-1.amazonaws.com/latest/install
chmod +x ./install
sudo ./install auto
systemctl start codedeploy-agent #running となていれば正常
その2
CodeBuild 作成時に考慮しなければならない点がいくつかあったので、ここにまとめて記載します。
まず、CodeBuild ではアーティファクトと呼ばれる処理の成果物を格納する、CodeBuild artifact 用のバケットを S3 に作成する必要があります。
CodeBuild artifact 用 S3バケットを作成後に CodeBuild でビルドプロジェクトを作成するわけですが、ここの【アーティファクト】設定項目で作成した S3バケットを選択します。
その他主な設定項目と今回設定した値は以下です。
【ソース】
ソースプロバイダ:AWS CodeCommit
リポジトリ:作成したリポジトリ
【Buildspec】
buildspec ファイルを使用する
【アーティファクト】
タイプ:Amazon S3
バケット名:CodeBuild 用に作成したS3バケット
次にCodeBuild 用に作成される IAMロール対して、(後続の) CodeDeploy に対するアクセス許可ポリシーを追加する必要があります。追加したポリシーは【AWSCodeDeployDeployerAccess】です。
最後、ビルドの実行に使用する YAML 形式のビルドコマンドを記述した buidspec.yaml を作成するのですが、以下の公式ドキュメントを参考にしながら、今回必要な箇所に抜粋しました。
まずは参考先の公式ドキュメント2つ。
その公式ドキュメントを参考に記述する内容が以下になるのですが、[CodeDeploy アプリケーション名]と[バケット名]は各々の環境に合わせて変化します。
また、[CodeDeploy アプリケーション名]についてはまだこの時点では作成されていないので、後続の実践で作成するものに変更する必要があります。
version: 0.2
phases:
build:
commands:
- aws deploy push --application-name [CodeDeploy アプリケーション名] --s3-location s3://[バケット名]/artifact.zip --source src
artifacts:
files:
- '**/*'
base-directory: src
その3
CodeDeploy を作成する前に、CodeDeploy 用 IAMロールの作成する必要がありますが、何も難しいことはありません。IAMロール作成画面でユースケース[CodeDeploy]を選択すると【AWSCodeDeployRole】が選択されている状態となっているのでそのまま作成すれば良いです。
CodeDeploy の作成も【アプリケーションの作成】から[アプリケーション名]と[コンピューティングプラットフォーム]を入力するだけです。
CodeDeploy作成後に【デプロイグループの作成】から【環境設定】で[Amazon EC2 インスタンス]を選択し対象のEC2インスタンスを選択すればまず形は整っている状態となります。
ここでまた YAML 形式のファイルを作成する必要があるのですが、今回は Cloud9 から[appsec.yml](アプリケーション仕様を記載するためのファイル)を作成し、以下を記述します。
version: 0.0
os: linux
files:
- source: index.html
destination: /var/www/html/
なお参考にした公式ドキュメントは以下です。
その4
CodeBuild から【ビルドを開始】することができます。が、私が最初に実行した時はエラーが出てしまいビルドを完了させることが出来ませんでした。
[Container] 2024/06/09 01:13:34.320799 Running on CodeBuild On-demand
[Container] 2024/06/09 01:13:34.320811 Waiting for agent ping
[Container] 2024/06/09 01:13:34.622517 Waiting for DOWNLOAD_SOURCE
[Container] 2024/06/09 01:13:41.211452 Phase is DOWNLOAD_SOURCE
[Container] 2024/06/09 01:13:41.212905 CODEBUILD_SRC_DIR=/codebuild/output/src3671662993/src/git-codecommit.ap-northeast-1.amazonaws.com/v1/repos/2112307_cicd-pipeline-handson
[Container] 2024/06/09 01:13:41.213374 YAML location is /codebuild/output/src3671662993/src/git-codecommit.ap-northeast-1.amazonaws.com/v1/repos/2112307_cicd-pipeline-handson/buildspec.yml
[Container] 2024/06/09 01:13:41.219817 Phase complete: DOWNLOAD_SOURCE State: FAILED
[Container] 2024/06/09 01:13:41.219847 Phase context status code: YAML_FILE_ERROR Message: did not find expected key at line 8
どうやら buildspec.yml 内のインデントが崩れていたようなので修正し、再試行を実行したら無事に成功しました。
その5
ここまで来ればあとは CodePipeline の作成でソース、ビルド、デプロイの各ステージで利用するリポジトリ、プロジェクト、アプリケーションを選択するだけで、CodePipeline が[git push]を自動検知し、デプロイまで自動で実行してくれる環境の構築が完了です。
CodePipeline に関しては(もっと複雑な構成だと話が変わってくるのでしょうが)これまでで一番設定がシンプルでした。
今後の課題
AWS の Code サービス群を利用した CI/CD 環境の構築を実践することが出来ましたが、やはりソフトウェア開発などの業務経験がないため、実業務ではどういう事に考慮して設計するのかだったり、裏ではどういう処理がされているのかをしっかりと理解できていない気がするので、ふわっとした理解で終わっているようにも感じます。
なので今後の課題としては、違う環境(例えばスケーラビリティな環境)でCI/CDパイプライン環境を構築したり、ソフトウェア開発について一から学んでいき理解を深めることも必要だと感じました。
まとめ
まとめと言えるのか微妙ですが、自動化って楽しいですね。自分はこれまでインフラ屋としてこれまでやってきたので、IaCはすごく興味があるので次は AWS CloudFormation の Hands-on for Beginners をやりたいなと思っています。
あとはコンテナね。