複数環境に対してCircleCI Workflowで同じコードをデプロイする(ElasticBeanstalk編)
概要
CircleCI Workflow ではテストを通した後に待たせておいて、任意のタイミングでワンクリックでデプロイするという方法をとることができます。
特に本番デプロイは手作業が多いと心理的負荷が高くて億劫になるので手順をできるだけ自動化したいです。
この記事では特に、AWS ElasticBeanstalk の複数の環境に同じバージョンのアプリケーションをデプロイする方法について書きます。ElasticBeanstalk以外でもworkflowの流れと、ジョブ間での情報の受け渡しの方法は同じなので応用できるかと思います。
具体的用途としては、以下のものを想定しています
- Webアプリケーションとジョブ実行するWorker環境の両方に同じコードを勝手にデプロイして欲しい
- 開発環境と本番環境の両方にワンクリックで同じコードをデプロイしたい
完成イメージ
こちらはCircleCI Workflow 実行時の画面イメージです。
dev の二つの環境にデプロイする場合には以下のような見た目になります。
テストが通った状態で止まっており、 require-testsのところがクリック可能になって、クリックするとデプロイが始まります(テスト終わった直後は一回リロードしないとクリック可能にならないのでそこだけ注意)
さらに本番へのデプロイを足した場合には以下のようになります。
新たに require-dev-deploy が足されており、それをクリックすることで本番デプロイに進むことができます。
設定の記述方法
.circleci/config.yml
に CircleCI Workflow の設定を書くことができます。
前提となるセットアップについては省略し、公式ドキュメントなどにお任せします。
ファイルの全体像がわかるように全部が入ったものを載せます。※
マークをつけたところについて個別の項目について解説をページ下部でつけました。
version: 2.1
# (※1) executors と commands について を参照のこと
executors:
setup-eb-environment:
docker:
- image: circleci/python:3.6.4
working_directory: ~/repo
commands:
setup-eb-command:
steps:
- checkout
# 今回の本流とは関係ないので一部省略。awscli入れて access key 設定などをします
- run:
name: Install awscli
jobs:
test-js:
# 今回は略
test-php:
# 今回は略
deploy-to-dev:
executor: setup-eb-environment
steps:
# 上で定義したコマンドを使っています
- setup-eb-command
- run:
name: Deploying to dev webapp
# ここでsedなどで出力整形するのもありではあるが、eb deploy コマンドの終了ステータスが破棄されてしまって異常時に正しく止まらないことが考えられたためファイルリダイレクトだけにしている
command: eb deploy develop-webapp > /tmp/eb_deploy_output
- run:
name: Deploying to dev worker
# こういう感じのアウトプットを期待してダブルクオートの中を取り出しています。 => Creating application version archive "app-2019-11-18-2-57-gd83f8-191122_104221".
command: |
cat /tmp/eb_deploy_output | grep "version archive" | sed -E 's/.*\"(.*)\".*/\1/' > /tmp/app_version_label
eb deploy develop-worker --label `cat /tmp/app_version_label`
- run:
name: check app version
command: cat /tmp/app_version_label
# (※2) job間での情報受け渡し方法について を参照のこと
- persist_to_workspace:
root: /tmp/
paths:
- app_version_label
deploy-to-production:
executor: setup-eb-environment
steps:
- setup-eb-command
- checkout
# workspaceに保存したものを取り出せます
- attach_workspace:
at: /tmp/
- run:
name: check app version
command: cat /tmp/app_version_label
- run:
name: Deploying to production worker
# (※3) ebコマンドの `--label` でのバージョン指定について を参照のこと
command: eb deploy production-worker --label `cat /tmp/app_version_label`
- run:
name: Deploying to production webapp
command: eb deploy production-webapp --label `cat /tmp/app_version_label`
workflows:
version: 2.1
build-and-test-approval-deploy:
jobs:
- test-js:
# (※4) filters の動きについて を参照のこと
filters:
tags:
only: /.*/
- test-php:
requires:
- test-js
filters:
tags:
only: /.*/
- require-tests:
type: approval
requires:
- test-php
filters:
tags:
only: /.*/
- deploy-to-dev:
requires:
- require-tests
filters:
tags:
only: /.*/
- require-dev-deploy:
type: approval
requires:
- deploy-to-dev
# リリースタグ 2019-11-01 や 2019-11-01-fix などの形に対応。tagがある時にだけリリース可能。
filters:
tags:
only: /^(\d){4}-(\d){2}-(\d){2}.*/
branches:
ignore: /.*/
- deploy-to-production:
requires:
- require-dev-deploy
filters:
tags:
only: /^(\d){4}-(\d){2}-(\d){2}.*/
branches:
ignore: /.*/
※1 executors と commands について
- executors は
Executors は、ジョブステップの実行環境を定義
- commands は
ジョブ内で実行するステップシーケンスをマップとして定義
要するに、実行環境とあとで使用するコマンドを先に定義しておいて、使いまわすことができます。
※2 job間での情報受け渡し方法について
永続化ではなくてジョブ間でのファイル受け渡しに persist_to_workspace(ファイルをworkspaceに30日保存) と attach_workspace(指定のパスに対してworkspaceにあったらアタッチする) のワンセットを使えることがわかった。
参考ドキュメント:
https://circleci.com/blog/build-cicd-piplines-using-docker/
https://circleci.com/docs/ja/2.0/configuration-reference/#persist_to_workspace
$BASH_ENV
に保存すれば良いという情報もあったが、$BASH_ENV
に保存されるファイルパスがジョブによって変わってしまって使えなかった。
※3 ebコマンドの --label
でのバージョン指定について
--label
を指定せずに eb deploy を複数回実行することもできるかと思いますが、それだと環境が増えるとElasticbeanstalkの管理コンソール上でみれるアプリケーションバージョンが複数発行されてしまい、邪魔になってしまいます。
--label
で以前のバージョンを指定すればその問題が起こりません。1回目の eb deploy のアウトプットを取得して整形し、2回目のeb deployコマンドの--label
オプションの引数に渡しています。
※4 filters の動きについて
参考: https://qiita.com/sanemat/items/4ddbd4016a5269265166
- branch はデフォルトで全て実行
- tag はデフォルトで全て無視
なのでtagのfilterを明示的に指定していない場合にgithubでタグが追加された時は最初のジョブからなくなるのでワークフローのリストにも表示されない。
そういうわけで、タグがついているタスクに対してジョブを実行したければ全てのジョブに以下のfilterを追加してあげる必要があった。
filters:
tags:
only: /.*/
おまけ CircleCI config のシンタックスチェック方法
circleci コマンドを用いると、いちいちデプロイしなくてもシンタックスチェックができて良いです。こういう仕事は大体時間がかかるので、待ち時間を減らしましょう。
$ circleci config validate -c .circleci/config.yml
Config file at .circleci/config.yml is valid.
このコマンドのインストール方法などは公式ドキュメントを参照のこと https://circleci.com/docs/ja/2.0/local-cli/
補足: mac PC の環境においてはbrewで入れると circleci update ができなかったのでbrew以外の方法で入れたほうが良さそう。
Author And Source
この問題について(複数環境に対してCircleCI Workflowで同じコードをデプロイする(ElasticBeanstalk編)), 我々は、より多くの情報をここで見つけました https://qiita.com/yamotuki/items/bdd425c5d980f51311f2著者帰属:元の著者の情報は、元のURLに含まれています。著作権は原作者に属する。
Content is automatically searched and collected through network algorithms . If there is a violation . Please contact us . We will adjust (correct author information ,or delete content ) as soon as possible .