Amazon EventBridge Scheduler から Amazon ECS Task を定期的に実行する構成を Terraform で構築する機会があったのでまとめておく❗️Amazon EventBridge Scheduler とても便利 \( 'ω')/
tf ファイル
最初に完成形の tf ファイルを載せておく❗️今回は Amazon EventBridge Scheduler にフォーカスするために Amazon VPC 関連(サブネットやセキュリティグループなど)と Amazon ECS Task 関連は準備できている前提として値をベタ書きしている.実際に組み込むときには変数などに置き換えてもらえればと👌 スケジューリングもドキュメントに載っている cron サンプルを使った.
ちなみに Amazon ECS Task Definition では hello-world image を動かすように作ってある🎲
data "aws_iam_policy_document" "scheduler_permissions" { version = "2012-10-17" statement { actions = [ "ecs:RunTask" ] resources = [ "arn:aws:ecs:ap-northeast-1:000000000000:task-definition/hello-world:*", "arn:aws:ecs:ap-northeast-1:000000000000:task-definition/hello-world" ] } statement { actions = [ "iam:PassRole" ] resources = ["*"] condition { test = "StringLike" variable = "iam:PassedToService" values = ["ecs-tasks.amazonaws.com"] } } } data "aws_iam_policy_document" "scheduler_assume" { statement { effect = "Allow" principals { type = "Service" identifiers = [ "scheduler.amazonaws.com", ] } actions = [ "sts:AssumeRole", ] condition { test = "StringEquals" variable = "aws:SourceAccount" values = ["000000000000"] } } } resource "aws_iam_role" "scheduler_role" { name = "scheduler-execution-role" inline_policy { name = "permissions" policy = data.aws_iam_policy_document.scheduler_permissions.json } assume_role_policy = data.aws_iam_policy_document.scheduler_assume.json } resource "aws_scheduler_schedule" "eventbridge_scheduler" { name = "scheduler" flexible_time_window { mode = "OFF" } schedule_expression = "cron(0/10 * ? * MON-FRI *)" schedule_expression_timezone = "Asia/Tokyo" target { arn = "arn:aws:ecs:ap-northeast-1:000000000000:cluster/cluster" role_arn = aws_iam_role.scheduler_role.arn ecs_parameters { task_definition_arn = "arn:aws:ecs:ap-northeast-1:000000000000:task-definition/hello-world:1" launch_type = "FARGATE" platform_version = "LATEST" network_configuration { subnets = ["subnet-xxxxxxxxxxxxxxxxx", "subnet-xxxxxxxxxxxxxxxxx"] security_groups = ["sg-xxxxxxxxxxxxxxxxx"] } } } }
アーキテクチャ図
ポイント1 : IAM Role(実行ロール)
Amazon EventBridge Scheduler の IAM Role は Amazon EventBridge Scheduler をコンソールで設定するときに自動的に作られる IAM Role Amazon_EventBridge_Scheduler_ECS_xxxxxxxxxx
を参考にした.ecs:RunTask
と iam:PassRole
は最低限必要で,あとはリソースや条件を細かく指定しておけば OK👌 最終的に作られるポリシーは以下のようになる❗️
{ "Version": "2012-10-17", "Statement": [ { "Action": "ecs:RunTask", "Effect": "Allow", "Resource": [ "arn:aws:ecs:ap-northeast-1:000000000000:task-definition/hello-world:*", "arn:aws:ecs:ap-northeast-1:000000000000:task-definition/hello-world" ] }, { "Action": "iam:PassRole", "Condition": { "StringLike": { "iam:PassedToService": "ecs-tasks.amazonaws.com" } }, "Effect": "Allow", "Resource": "*" } ] }
ポイント2 : Amazon EventBridge Scheduler(タイムゾーン)
Amazon EventBridge Scheduler で便利なのは「タイムゾーン」のサポートで,Amazon EventBridge Rules のように UTC に悩むことなく Asia/Tokyo を指定できる✌️
schedule_expression_timezone = "Asia/Tokyo"
ポイント3 : Amazon EventBridge Scheduler(スケジューリング)
スケジューリング設定では cron()
で cron 式を使える.
schedule_expression = "cron(0/10 * ? * MON-FRI *)"
もし規則的な実行をするだけで良いなら rate()
を使えばもっとシンプルに書ける❗️
schedule_expression = "rate(10 minutes)"
ポイント4 : Amazon EventBridge Scheduler(フレックスタイムウィンドウ)
デフォルトではオフだけど,フレックスタイムウィンドウを設定すると開始時刻を「ズラして」フレックスタイムウィンドウ内の "どこかしらで" 実行できる.レート制限があったりする場合に使える❗️
flexible_time_window { mode = "FLEXIBLE" maximum_window_in_minutes = 2 }
ポイント5 : Amazon EventBridge Scheduler(Amazon ECS RunTask API)
Amazon EventBridge Scheduler のターゲットとして Amazon ECS RunTask API を実行する場合は ecs_parameters
ブロックで詳細な設定をする.今回は主に以下を設定した.設定できる項目の一覧は Terraform Registry のドキュメントに載っている📝
task_definition_arn
(ECS Task Definition の ARN)launch_type
(起動タイプをEC2
/FARGATE
/EXTERNAL
から選ぶ)platform_version
(Fargate プラットフォームバージョンをLATEST
や1.4.0
のように設定する)network_configuration
(サブネット・セキュリティグループ・パブリック IP を設定する)
関連記事
AWS EventBridge Terraform module を使って構築するなら以下の記事も読んでもらえればと💡