こんにちは、開発部の根岸(@negipo)です。ここ最近はプログラムより小説をたくさん書いている気がします。先日発売されたSFマガジン2021年2月号にぼくの小説が載っているので、SFに興味がある方はぜひ買ってください。
さて、この記事をお読みの皆さんはアプリケーションを運用されているでしょうか。こたえは当然イエスでしょう。内製にしろOSSにしろ監視にしろジョブ管理にしろ、我々が日々おこなうエンジニアリングの多くはアプリケーションを運用することによって成立しています。
一方で、アプリケーションの運用において、なにか目的があってアプリケーションの設定を変更しようとするとき、実体のあるファイルの編集ではなくサービスのユーザーインターフェースを介した変更を求められることがあります。逆向きに捉えれば、そのようなインターフェースが準備されているという事実は、我々がそのアプリケーションに対して頻繁な設定の変更を求めているということを示しています。アプリケーションが達成したい価値は多様で、その解決方法も様々です。
ユーザーインターフェースを介して設定変更をもとめるようなアプリケーションを運用するとき、大規模な変更は、たとえば操作内容のレビューの観点において難しいです。では、そのときに、アプリケーションがユーザーインターフェースによって隠蔽している設定内容をテキストファイルにダウンロードし、Gitリポジトリ管理する実装が準備されていたとしたら、何が起きるでしょうか。GitHub上のレビュー可能性など、リポジトリ管理に伴ってあらわれる特徴を通して、多様な観点から運用を改善することが可能になると想像できます。
本稿では、ロコガイドが利用しているジョブ管理ツールのkuroko2を対象に、アプリケーション設定のリポジトリ化をもちいて実際に運用を改善した事例を紹介し、その価値について論じたいと思います。
起きていた問題と解決方針
kuroko2のジョブ定義のためのタスク記法には、リトライやエラー発生時の挙動、実行時間に基づいた警告などの設定が含まれています。kuroko2はウェブベースのGUIを提供しており、ユーザーはジョブ定義をテキストエリアに書き込んで保存することでワークフローの挙動を変更します。
さて、ロコガイドでは最近になって適切ではないジョブ定義に起因すると思われる警告や実行の失敗が多く見られるようになり、対応のため失敗数や警告数などの棚卸しをおこなって、精査の結果相当数のジョブを対象に設定を書き換えることになりました。大規模に多様な担当者が運用しているジョブをまとめて変更するのははじめてであり、作業者には運用されているバッチジョブの運用知識が薄いため、原則として担当者にレビュー依頼をおこない、不測の事態を避けることになります。これまで、単一ジョブの設定変更の際には、設定前後の差分を取ってGitHubのIssueコメントに貼りレビュー依頼するなどのフローを取る事例があった一方、固まったレビューフローは存在していませんでした。
今回、kuroko2から設定をダウンロードして、ファイルとして一定の形式で保存するRakeタスクを整備し、両者をGitリポジトリ化してGitHubに配置することで、普通のアプリケーションを実装するときのようにkuroko2の設定をレビュー可能にするという方針を立てました。変更するジョブごとにプルリクエストを分割すれば、今回のようなケースでもコンテキストをうまく切り分けられ、議論が容易になると思われます。
実装
設定をkuroko2のデータベースから直接ダウンロードするRakeタスクを作り、リポジトリ化しました。設定の反映についてはデータベースを直接編集する場合に起きうる問題(kuroko2が管理している履歴への追加漏れなど)を考慮し、現状ではRakeタスクは実装されていません。
実装されたRakeタスクは下記のとおりです。
rake download[id] # ジョブ定義を一つだけdownload rake download_all # ジョブ定義をすべてdownload rake setup # setup
このRakeタスクの実行後には、以下のようにjob_definitions
以下にジョブ定義IDごとにジョブの内容説明とリポジトリ化されたタスク記述が配置されます。
├── Rakefile ├── job_definitions │ ├── 1 │ │ ├── README.md │ │ └── script.txt # タスク記述 │ ├── 2 │ │ ├── README.md │ │ └── script.txt │ └── ... └── lib └── ...
よって、ジョブ定義を記述する際に以下のような固いレビューフローを組むことが可能になりました。
- 新規作成をおこなう際
- kuroko2上でテンプレートに従ってジョブをサスペンド状態のまま作成する
- Rakeタスクでジョブ定義をリポジトリにダウンロードする
- プルリクエストを作成する
- レビュー
- マージ
- ジョブのサスペンドを解除
- 変更をおこなう際
- ジョブ定義をリポジトリ上で編集する
- プルリクエストを作成する
- レビュー
- マージ
- kuroko2のインターフェースから変更を反映
評価
利用しているジョブ管理ツールの大規模な設定変更がレビュー可能になり、設定の反映に伴って運用上の問題が軽減しました。リポジトリに基づいたレビューフローは開発チームに共有され、引き続き運用されています。また、レビューフローを整備したことでジョブ管理に伴う様々な方針を積極的にレビューする文化が醸成され、あらたな運用上の問題が発生しにくく、発生時の解決もより容易になったと認識しています。
終わりに
解決手法の発想には、Infrastructure as codeや、すでにロコガイドでおこなわれている静的配信ファイルの管理フロー(今回の実装と同様に、S3に配置されているファイルとRakeタスクが実装されているリポジトリがあり、作業者はレビューを経て反映する)が念頭にありました。実装自体は非常に簡易なもので、野蛮ですが、実効性がありました。
固まった手順を破壊してあらたなワークフローを導入することには勇気が必要ですが、より良い発想を実行できるよう、常に鋭敏でありたいと思います。