☕️

ecspresso advent calendar 2020 day 11 - verify

2020/12/11に公開

Amazon ECS のデプロイツールである ecspresso の利用法をまとめていく ecspresso Advent calendar 11日目です。

ECSのタスクは、それ単体では動作しません。タスクが動作するための依存リソースが事前に存在している必要があります。

  • タスクが動作する IAM ロール(タスクロール)を指定した場合には、そのロールが事前に必要です
  • タスクを実行する EC2 インスタンスや Fargate の実行基盤が使用するためのタスク実行ロールも必要になることがあります
  • タスクで利用するコンテナイメージは Amazon ECR (Elastic Container Registory) や DockerHub などに存在している必要があります
  • ログを CloudWatch Logs に出力する設定を行った場合は
    1. 事前にロググループが存在し
    2. タスク実行ロールの権限でそのロググループに対してログストリームの作成ができ
    3. ログの送信を行える必要があります

これらの各種リソースが存在していなかったりアクセス権がなかったりすると、タスクは実行できません。タスク定義の登録時にはこれらの外部リソースはチェックされないため、不備は実際に実行してみないと気がつけないことが多くあります。

実行前に各種リソースが利用可能かを検証できれば、タスクを起動してみて失敗する可能性を減らせます。ecspresso v1.2.0 ではそのために verify コマンドをサポートしました。

サービス/タスク定義が依存するAWS上の各種リソースが利用可能か検証する verify コマンド

verify コマンドは、サービス/タスク定義を解析し、依存リソースが存在しているか、実際にアクセスできるかを検証します。

v1.2.1 の時点では、以下の項目を検証しています。

  • タスクロール、タスク実行ロールが存在し、ecs-tasks.amazonaws.com によって引き受け(Assume Role)可能である
  • コンテナ定義内で
    • コンテナイメージとタグが存在する
      • DockerHub の public image、ECR の image のみ確認できます
    • ロググループが存在し、ログストリームを作成し、ログを送信できる
      • デフォルトでは実際にログを送信して検証します
    • secrets の項目が SSM パラメータストアもしくは SecretsManager に存在し、読み取り可能である
      • KMS で暗号化されている場合、実際に復号できるかも確認します
  • (ロードバランサー配下のサービスの場合)ターゲットグループが存在している
  • ECS クラスタが存在している

タスク実行ロール(taskExecutionRole)が定義されている場合は、ecspresso が実行している権限でタスク実行ロールに Assume Role を試みます。

成功した場合には、タスク実行ロールの権限で検証を行います。そのため、実際のタスク実行ロールからロググループやsecretsへアクセス可能な権限があるかも検証できます。

タスク実行ロールへの Assume に失敗した場合は、現在の権限でそのまま検証を続行します。そのため、この状態で検証が成功しても実際にタスクを実行するロールで正常に動作するかは確実ではありません。

実行例

正常にタスク実行ロールに assume role できて、検証が成功した場合の例を示します。

$ ecspresso --config config.yaml verify
2020/12/11 16:21:08 nginx-service/ecspresso-demo Starting verify
  TaskDefinition
    ExecutionRole[arn:aws:iam::123456789012:role/ecsTaskExecutionRole]
    --> [OK]
    TaskRole[arn:aws:iam::123456789012:role/ecsTaskRole]
    --> [OK]
    ContainerDefinition[nginx]
      Image[nginx:latest]
      --> [OK]
      LogConfiguration[awslogs]
      --> [OK]
    --> [OK]
  --> [OK]
  ServiceDefinition
    LoadBalancer[0]
    --> [OK]
  --> [OK]
  Cluster
  --> [OK]
2020/12/11 16:21:12 nginx-service/ecspresso-demo Verify OK!

assume role ができなかった場合でも、現在の権限で検証を続行します。

$ ecspresso --config config.yaml verify --no-put-logs
WARNING: failed to assume role to taskExecutuionRole. Continue to verifiy with current session.
AccessDenied: User: arn:aws:iam::123456789012:user/xxxx is not authorized to perform:
sts:AssumeRole on resource: arn:aws:iam::123456789012:role/ecsTaskExecutionRole
        status code: 403, request id: 99015bdb-5a6f-4be7-80d7-42874a74ec7c
2020/12/11 16:40:36 nginx-service/ecspresso-demo Starting verify
  TaskDefinition
    ExecutionRole[arn:aws:iam::123456789012:role/ecsTaskExecutionRole]
    --> [OK]
    TaskRole[arn:aws:iam::123456789012:role/ecsTaskRole]
    --> [OK]
    ContainerDefinition[nginx]
      Image[nginx:latest]
      --> [OK]
      LogConfiguration[awslogs]
      --> LogConfiguration[awslogs] [SKIP] putting logs to /ecs/first-run-task-definition
    --> [OK]
  --> [OK]
  ServiceDefinition
    LoadBalancer[0]
    --> [OK]
  --> [OK]
  Cluster
  --> [OK]
2020/12/11 16:40:39 nginx-service/ecspresso-demo Verify OK!

注意点

IAMのマネージドポリシーである AmazonECSTaskExecutionRolePolicy には、ロードバランサーへの読み取り権が附与されていません。タスク実行ロールにはロードバランサーの読み取り権限は不要ですが、ecspresso verify でターゲットグループの確認をするためには必要です。

ターゲットグループの検証が elasticloadbalancing:DescribeTargetGroups 権限がないという理由で失敗する場合には、タスク実行ロールに elasticloadbalancing:DescribeTargetGroups もしくはマネージドポリシーの ElasticLoadBalancingReadOnly を附与してください。

verify コマンドのオプション

usage: ecspresso verify [<flags>]

verify resources in configurations

Flags:
  --help           Show context-sensitive help (also try --help-long and --help-man).
  --config=CONFIG  config file
  --debug          enable debug log
  --color          enalble colored output
  --put-logs       put verification logs to CloudWatch Logs

--put-logs

コンテナのログを CloudWatch Logs に出力する設定の場合、デフォルトでは実際にロググループに対して {prefix}-ecspresso-verify-xxx というログストリームを作成し、This is a verify message by ecspresso というログを書き込みます。

検証時に実際にログを送信したくない場合には、--no-put-logs を指定してください。

--color

出力結果を色つきにします。端末で実行されている場合にはデフォルトで有効、端末以外で実行されている場合にはデフォルトで無効 (--no-color) になります。


12日目は、設定ファイル上のサービス/タスク定義を、テンプレート記法を適用してレンダリングする方法について説明します。

https://zenn.dev/fujiwara/articles/ecspresso-20201212

Discussion