CircleCI Enterprise版 Builderインスタンスの安全なスケールイン方法

 ツイート 3  シェア 2  Hatena 0

2018年12月3日に「CircleCI Japan ユーザコミュニティキックオフ」というイベントがあり、そこで CircleCI Enterprise 管理者向けの話として、Builderインスタンスのスケールインの方法について話してきました。当日の資料と、補足の情報を残しておきます。

Builder インスタンスをスケールインさせる方法は Introduction to Nomad Cluster Operation – CircleCI に数行でちょろっと書かれているだけなので、細かい実装方法の参考になれば嬉しいです。

目次

  1. AWS で自動化する場合の補足

AWS で自動化する場合の補足

資料の中で一番情報量の多い AWS の自動化のページの補足です。利用している AWS サービスや API のリンクをまとめました。

AWSで自動化する例

AutoScalingGroup の Desired capacity を減らす

Desired capacity の操作は AutoScalingGroup の Scheduled Action を使って操作しています。朝9時に2台にして、昼前に5台に増やして、お昼休みに2台に減らして、という感じです。
Amazon EC2 Auto Scaling のスケジュールに基づくスケーリング – Amazon EC2 Auto Scaling (日本語)

AutoScaling の LifecycleHook でインスタンスの Terminating 状態をフックし、SQS にメッセージを送る

インスタンスの停止をフックして、停止するまでの間に処理を挟み込むことができます。この後 Lambda に処理を行わせるので、通知先を SQS にしておきます。
Amazon EC2 Auto Scaling ライフサイクルフック – Amazon EC2 Auto Scaling (日本語)

SQS から Lambda を起動

SQS から Lambda を起動するように設定します。SQL から Lambda を起動すると、リトライ処理を SQS に任せることができて、Lambda のコード量が減ります。
AWS Lambda を Amazon SQS に使用する – AWS Lambda

イレギュラー時に Lambda が何度もリトライを繰り返して「終了しないループ」に入ってしまうことがありますので、ループしないように Lambda のコードに抜け道を作っておく、キュー内のメッセージの保存期間を短めにしておく、デッドレターキューを使うなどの対策が必要です。

Lambda で Nomad の Drain API の実行

Lambda で Nomad Drain API を叩くには、少し工夫が必要です。

Nodes Drain node – HTTP API – Nomad by HashiCorp から Drain API 仕様を確認すると、Path が /v1/node/:node_id/drain となっていて、API を叩くために node_id が必要です。node_id とは Nomad Client を識別する ID です。SQS からは終了予定のインスタンス ID しか情報が渡ってこないので、インスタンス ID を頼りに node_id を取得する必要があります。

node_id は以下のようにして取得することができます。

  1. AWS SDK を使って、インスタンス ID から privateDNSName を取得する
  2. Nodes – HTTP API – Nomad by HashiCorpを叩く
  3. レスポンスID に node_id が、Name にホスト名が入っているので、privateDNSName の値でレスポンスの json をフィルタリングして node_id を取得する

node_id が取れたら、それを使って Nodes Drain node – HTTP API を叩きます。

Lambda でビルドが実行中かどうか調べる

Drain モードにできたら、Nomad の Allocations API を使って終了予定のインスタンス内でビルドが実行中かどうか調べます。
Allocations – HTTP API – Nomad by HashiCorp

Allocations API の レスポンス にある ClientStatus から調べることができます。

ビルドが実行中だったら Lambda をエラーで終了させる

Lambda をエラーで終了させると、SQS にメッセージが戻り、Lambda がリトライされます。リトライ間隔を伸ばしたい場合は、Amazon SQS 可視性タイムアウト – Amazon Simple Queue Service を少し長めに設定します。

ビルドが実行されていなかったら AutoScaling に完了を通知する

AWS SDK で LifecycleHook に完了を通知します。
Amazon EC2 Auto Scaling ライフサイクルフック – Amazon EC2 Auto Scaling (日本語)

Lambda を正常終了させると SQS からメッセージが自動的に削除されます。

 ツイート 3  シェア 2  Hatena 0