SHOEISHA iD

※旧SEメンバーシップ会員の方は、同じ登録情報(メールアドレス&パスワード)でログインいただけます

DeveloperZine(デベロッパージン)- エンジニアの意思決定を支える技術情報メディア ProductZine

CodeZine編集部では、現場で活躍するデベロッパーをスターにするためのカンファレンス「Developers Summit」や、エンジニアの生きざまをブーストするためのイベント「Developers Boost」など、さまざまなカンファレンスを企画・運営しています。

エンジニアのためのCI/CD再入門

モダンなCI/CDでは欠かせないワークフローを使った高度なビルド管理

エンジニアのためのCI/CD再入門 第3回


失敗したワークフローの再実行

 ワークフローを使って設定を分割する利点は他にもあります。ワークフローの途中でジョブが失敗したときは再実行が簡単になるという利点です。

 これはCircleCIの開発チームで仕事をしていた時の話ですが、ビルドからデプロイまでに約50分かかるプロジェクトがありました。さらに、End to Endテストの信頼性が低かったため、時々ランダムなエラーが発生してビルドが失敗するという現象が発生していました。失敗すると開発者はビルドを再実行して、2回目は問題なく通るといった具合です。ワークフローがない場合はすべての処理が1つのビルドの中に入っているため、ランダムなエラーでビルドが失敗した際は、また最初からビルドを実行する必要があるので全体の開発スピードがスローダウンしていました。

 ワークフローを使えば失敗したジョブから再実行することができます。例えば、End to Endテストを1つのジョブに切り出せば、もしランダムなエラーで失敗した場合でも、そこから再実行ができます。

 失敗したジョブの再実行はCircleCIではとても簡単です。失敗したジョブのワークフロー画面へ行き、"Rerun from failed"を選択します。もし、すべてのジョブを最初から実行したい際は"Rerun from beginning"を選んでください。

 CI/CDの基本は決定的、つまり実行結果が常に同じにならないといけません。再実行したら2回目は成功した、というのは本来はよくないのですが、開発の現場ではよくあることです。何度も同じジョブがランダムに失敗するときは見直しが必要ですが、なんらかの理由でたまたま失敗してしまったときはとても便利な機能なので覚えておいてください。

rerun
rerun

ワークスペース

 複数のジョブに分けて管理していくと、時々ジョブの間でデータの受け渡しをしたくなる時があります。こんなときはワークスペースを使えば実現できます。よくある使い所としては、最初にコードをコンパイルして、後のジョブでそれを使うことで各ジョブでコンパイルを省略する使い方です。

 ワークスペースとは、あるワークフローが実行されている間だけ有効な共有ファイルストレージと考えると分かりやすいかもしれません。ジョブ間でファイルのやりとりをしたい場合、前のジョブがファイルをこの共有ストレージにアップロードして、後のジョブはここからダウンロードすることができます。CircleCIのワークスペースではアップロードをpersistと呼びダウンロードをattachと呼びます。

 では、実際にワークスペースを使ってみましょう。RailsのアプリではしばしばJavaScriptやCSSなどのアセットをプリコンパイルしたものを本番環境にデプロイすることがあります。今回のブログアプリでも同じことができるので、それを使ってワークフローの機能を試してみましょう。アセットをプリコンパイルするprecompileジョブとデプロイするdeployジョブを新たに追加して、これらのジョブ間でアセットを渡してみます。

 なお、本来であればdeployステップには実際のデプロイ環境に応じたコマンドを書くのですが、実際にデプロイしようとすると解説が複雑になってしまうため、ここでは擬似的なデプロイにとどめておきます。HerokuなどにRailsアプリをデプロイする際はプリコンパイルされたアセットも一緒にデプロイするという方法があるので、今回はそれを真似てプリコンパイルされたアセットがdeployジョブに渡されていることを確認するだけにしましょう。

precompile:
  ...
  steps:
    ...
    - run: bundle exec rake assets:precompile RAILS_ENV=production

    - persist_to_workspace:
        root: public/
        paths:
          - assets

deploy:
  ...
  steps:
    - attach_workspace:
        at: public

    - run: ls -la public/assets

 ここも紙面節約のために完成形の.circleci/config.ymlへのリンクを掲載しておき、ポイントだけを解説します。

- run: bundle exec rake assets:precompile RAILS_ENV=production

 アセットをプリコンパイルするコマンドです。これを実行するとpublic/assetsというディレクトリにアセットが生成されます。

- persist_to_workspace:
    root: public/
    paths:
      - assets

 persist_to_workspaceを使うとワークスペースにファイルをアップロードします。rootでアップロードするファイルが存在するルートディレクトリを指定しpathsで実際にアップロードするファイルを指定します。今回の場合だとpublic配下にはassetsディレクトリの他にもファイルがありますが、今回アップロードしたいのはアセットのみなのでassetsを指定しています。

 次にデプロイジョブを見てみましょう。

- attach_workspace:
    at: public

 attach_workspaceを使うとワークスペースにあるファイルをダウンロードすることができます。atは実際にダウンロードする場所を指定します。成功すれば precompileジョブで生成されたアセットがちゃんとdeployジョブに渡されていることが確認できます。

attach_workspace
attach_workspace

Fan-in/Fan-outについて

 パイプラインで覚えておきたい用語の一つにFan-in/Fan-outというものがあります。Fan-inは複数のジョブが完了したあと1つのジョブを実行するパイプラインのことを言います。Fan-outは逆で1つのジョブの完了を待って、複数のジョブを実行するパイプラインです。今回の例だとinstall_dependencyからrun_test/run_lint/precompileへの流れはFan-outで、そこからdeployへの流れはFan-inになります。覚えにくい場合は、Fan-inは"すぼむ"、Fan-outは"ひろがる"、というイメージを持つと覚えやすいかもしれません。

fan-in-fan-out
fan-in-fan-out

次のページ
ワークスペースとキャッシュ

修正履歴

この記事は参考になりましたか?

エンジニアのためのCI/CD再入門連載記事一覧

もっと読む

この記事の著者

金 洋国(CircleCI Japan)(キム ヒロクニ)

CircleCIで2.0などのプロダクト開発に携わった後、CircleCI Japanを立ち上げてからはTech Leadとして技術全般を担当。趣味は電動キックボードで日本で普及するように様々な活動をしています。

※プロフィールは、執筆時点、または直近の記事の寄稿時点での内容です

この記事は参考になりましたか?

この記事をシェア

CodeZine(コードジン)
https://codezine.jp/article/detail/11306 2019/01/16 10:41

イベント

CodeZine編集部では、現場で活躍するデベロッパーをスターにするためのカンファレンス「Developers Summit」や、エンジニアの生きざまをブーストするためのイベント「Developers Boost」など、さまざまなカンファレンスを企画・運営しています。

新規会員登録無料のご案内

  • ・全ての過去記事が閲覧できます
  • ・会員限定メルマガを受信できます

メールバックナンバー