ECSのデプロイを待つとき、aws ecs wait services-stableだけでは不十分な場合がある

こんにちは。 エキサイト株式会社の三浦です。

ECSにAWS CLIを使ってデプロイするとき、皆さんはデプロイの完了をどうやって検知しますか?

今回は、デプロイ完了検知に aws ecs wait services-stable を使用したときの問題点について説明します。

AWS CLIとECSへのデプロイ

ECSへのデプロイ方法はいくつかありますが、その中の一つにAWS CLIを使用するというものがあります。

aws ecs update-service \
    --cluster クラスタ名 \
    --service サービス名 \
    --task-definition タスク定義のARN

これだけでECSへのデプロイが実現できるので、AWS CLIのインストールやAWS環境への認証さえ行っていれば、非常にお手軽なデプロイ方法になります。

ただし、このコマンドはデプロイは実行してくれるものの、デプロイの完了を待たずにコマンド実行を終了してしまうため、実際にデプロイが完了したかを待つためには別の方法を取る必要があります。

そのために、 aws ecs wait services-stable というコマンドが用意されています。

aws ecs wait services-stable  \
    --cluster クラスタ名 \
    --service サービス名

このコマンドは、実行すると「ECSサービスが安定化」するまで待ち続けてくれるため、 aws ecs update-service 実行後にこのコマンドを実行することで、デプロイを待ってくれます。

これで一見問題ないように見えますが、実は「ECSサービスが安定化」するという定義が少し曲者で、そのせいで aws ecs wait services-stable だけではデプロイを待つのに不十分な場合があります。

ALBを使用したECSへのデプロイでの問題点

aws ecs wait services-stable における「ECSサービスの安定化」とは、以下のような定義になります。

awscli.amazonaws.com

Wait until JMESPath query length(services[?!(length(deployments) == 1 && runningCount == desiredCount)]) == 0 returns True

上記の通り、実はこのコマンドはALBのヘルスチェック等は特に見ておらず、あくまでECS上で deployments の数が1つだけで、 runnningCountdesiredCount の数が同じ、というところしか見ていません。

そのため、例えばALBと接続したECSで「ヘルスチェックの猶予期間」等を長めに指定していたために、ALBのヘルスチェックが通ったかはまだ確定していないものの、ECSの上記のパラメータだけは問題ない数値に落ち着いてしまった場合、 aws ecs wait services-stable は「成功した」として終了してしまうのです。

そういった意味では、残念ながらALBを使用したECSへのデプロイでは、 aws ecs wait services-stable による待機だけでは不十分ということになります。

なにか別の方法で、ALBのヘルスチェックが通ったことを検知する必要があるでしょう。

最後に

aws ecs wait services-stable のこの仕様は、特に不具合というわけではないと思われます。

というのも、ECSは必ずしもALBを使う必要がないサービスであり、ALBを使わないのであれば現在の挙動で十分だからです。

必要に応じて、必要な検知方法を検討・使用して行きましょう。