EventBridgeでECSタスクを自動実行する構築手順と権限設計

はじめに

AWS上で定期的なバッチ処理を運用する際、Amazon EventBridgeとAmazon ECS (Fargate) を組み合わせる構成は非常に一般的です。サーバーレスでスケールし、インフラ管理の手間を最小限に抑えられる点が大きな魅力です。

しかし、初学者や中級者がハマりがちなポイントとして「IAMロールの設定不備」や「ネットワーク接続エラー」があります。本記事では、EventBridgeからECSタスクを安全かつ確実に自動実行するための構築手順と権限設計のベストプラクティスを分かりやすく解説します。

前提知識/必要な理由

バッチ処理を安定して稼働させるためには、適切な権限分離と適切なインフラ構成の理解が不可欠です。本構成において重要な要素は以下の通りです。

  • Amazon EventBridge: 特定のスケジュール(Cron形式など)でイベントを発火し、ECSタスクの起動をキックします。
  • Amazon ECS (Fargate): サーバーのプロビジョニングなしでコンテナを実行する環境を提供します。
  • 3つのIAMロールの明確な分離: 権限不足によるエラーを防ぐため、「タスク実行ロール」「タスクロール」「EventBridge用ロール」の役割を正しく理解する必要があります。

具体的な設定手順・設計方法

ここからは、実際に環境を構築する手順をステップバイステップで説明します。

ステップ1: コンテナイメージの準備とECRへのプッシュ

まずはバッチ処理を実行するコンテナイメージを作成します。ここではPythonで外部API(例: データ取得や外部通知)を叩く処理を想定します。

スクリプト内で標準ライブラリ外のサードパーティ製パッケージである requests を使用する場合、コンテナ内にインストールする手順が必要です。

実行用コード(app.py):

import requests
import sys

def main():
    print("バッチ処理を開始します。")
    # 例として外部APIにリクエストを送信
    response = requests.get("https://api.github.com")
    print(f"ステータスコード: {response.status_code}")
    print("バッチ処理が正常に完了しました。")

if __name__ == "__main__":
    main()

Dockerfile の作成(サードパーティ製ライブラリ requests の導入補足手順を含めます):

FROM python:3.11-slim

WORKDIR /app

# pipコマンドによる外部パッケージ requests のインストール
RUN pip install --no-cache-dir requests

COPY app.py .

CMD ["python", "app.py"]

ビルドと Amazon ECR へのプッシュ手順:

# ECRリポジトリへのログイン
aws ecr get-login-password --region ap-northeast-1 | docker login --username AWS --password-stdin <AWS_ACCOUNT_ID>.dkr.ecr.ap-northeast-1.amazonaws.com

# イメージのビルド
docker build -t my-batch-app .

# タグ付けとECRへのプッシュ
docker tag my-batch-app:latest <AWS_ACCOUNT_ID>.dkr.ecr.ap-northeast-1.amazonaws.com/my-batch-app:latest
docker push <AWS_ACCOUNT_ID>.dkr.ecr.ap-northeast-1.amazonaws.com/my-batch-app:latest

ステップ2: IAMロールの設計と作成

実務で最もトラブルが起きやすいIAMロールを3種類作成します。

  • 1. タスク実行ロール (ecsTaskExecutionRole): ECSエージェントがECRからイメージを引き引いたり、CloudWatchにログを送信するためのロール。AWS管理ポリシー AmazonECSTaskExecutionRolePolicy をアタッチします。
  • 2. タスクロール (ecsTaskRole): コンテナ内部のアプリ(app.py)がS3やDynamoDB等のAWSサービスを操作するためのロール。必要最小限の権限を定義します。
  • 3. EventBridge用実行ロール (eventBridgeEcsExecutionRole): EventBridgeが指定されたECSタスクを起動(ecs:RunTask)し、ECSにIAMロールを渡す(iam:PassRole)ためのロール。

EventBridge用ロールに付与するインラインポリシーの例:

{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Action": "ecs:RunTask",
      "Resource": "arn:aws:ecs:ap-northeast-1:<AWS_ACCOUNT_ID>:task-definition/my-batch-task:*"
    },
    {
      "Effect": "Allow",
      "Action": "iam:PassRole",
      "Resource": [
        "arn:aws:iam::<AWS_ACCOUNT_ID>:role/ecsTaskExecutionRole",
        "arn:aws:iam::<AWS_ACCOUNT_ID>:role/ecsTaskRole"
      ]
    }
  ]
}

ステップ3: ECSタスク定義の作成

作成したECRイメージURLやログ出力先(CloudWatch Logs)、ステップ2で用意したIAMロールを指定してタスク定義を登録します。

ステップ4: EventBridge スケジュールルールの作成

EventBridgeコンソールからルールを作成し、Cron式(例: cron(0 0 * * ? *) で毎日UTC 0:00 / JST 9:00に実行)を設定します。

ターゲットに「Amazon ECS タスク」を選択し、以下の項目を正確に設定します。

  • クラスタとタスク定義の選択
  • 起動タイプ: FARGATE
  • ネットワーク構成: VPC、サブネット、セキュリティグループの指定
  • IAMロール: ステップ2で作成した eventBridgeEcsExecutionRole を指定

実務での注意点

本番運用において落とし穴になりやすい注意点を2点紹介します。

1. アウトバウンド通信とSubnet設定

Fargateタスクがパブリックサブネットに配置されている場合、Auto-assign public IP(パブリックIPの自動割り当て)を有効(ENABLED)にする必要があります。これを行わないとECRからのイメージ取得に失敗してタスクが起動しません。プライベートサブネットで起動する場合は、NAT Gateway または VPC エンドポイント(ECR、S3、CloudWatch Logs用)の設置が必須となります。

2. タスク失敗時の検知(DLQとアラート)

EventBridgeのターゲット設定でデッドレターキュー(SQS)を設定しておくことで、API上限や一時的な障害でECSタスクの起動要求自体が失敗した場合に通知を受け取ることができます。また、コンテナの処理エラー(Exit Code 1など)はCloudWatch LogsのメトリクスフィルターとSNS連携を用いて検知する仕組みを構築しましょう。

まとめ

Amazon EventBridgeとECS Fargateを用いた定期バッチ処理は、サーバーレスで信頼性の高いインフラを構築できる強力な構成です。

構築のポイントは「3つのIAMロールの権限分離」と「適切なネットワーク設計」です。これらを理解し、エラー検知の仕組みまで含めて自動化しておくことで、実務で安心して運用できる堅牢なバッチ基盤を実現できます。

上部へスクロール