EventBridge Scheduler is actually a separate, more powerful service than EventBridge Rules, and you’re probably looking for that.

Here’s how you can run ECS tasks on a schedule using EventBridge Scheduler.

Let’s say you want to run a batch job every night at 2 AM to process some data.

aws scheduler create-schedule \
    --name "daily-ecs-processing-job" \
    --flexible-time-window Mode=OFF \
    --schedule-expression "cron(0 2 * * ? *)" \
    --start-after 1678886400 \
    --end-after 1710422400 \
    --target '{
        "Arn": "arn:aws:ecs:us-east-1:123456789012:task-definition/my-processing-task:1",
        "RoleArn": "arn:aws:iam::123456789012:role/EventBridgeSchedulerECSTaskRole",
        "EcsParameters": {
            "TaskDefinitionArn": "arn:aws:ecs:us-east-1:123456789012:task-definition/my-processing-task:1",
            "TaskCount": 1,
            "LaunchType": "FARGATE",
            "NetworkConfiguration": {
                "AwsVpcConfiguration": {
                    "Subnets": ["subnet-012345abcdef67890", "subnet-fedcba0987654321"],
                    "SecurityGroups": ["sg-0987654321abcdef"],
                    "AssignPublicIp": "ENABLED"
                }
            }
        },
        "Input": "{\"command\": [\"process\", \"--daily\"]}"
    }' \
    --kms-key-arn "arn:aws:kms:us-east-1:123456789012:key/your-kms-key-id" \
    --state ENABLED

This create-schedule command sets up a recurring event. The schedule-expression uses a cron syntax for "at 2:00 AM every day." flexible-time-window set to OFF means it will run exactly at the scheduled time, not within a window. start-after and end-after define the operational window for this schedule in Unix epoch time.

The target is where the magic happens. We specify the ARN of your ECS task definition. RoleArn is crucial; it’s the IAM role EventBridge Scheduler will assume to launch ECS tasks. EcsParameters lets you fine-tune how the task runs: TaskDefinitionArn (again, for clarity and validation), TaskCount, LaunchType (Fargate or EC2), and NetworkConfiguration (subnets, security groups, public IP assignment) are all defined here. The Input field allows you to pass JSON parameters to your ECS task, which your task’s entrypoint can parse.

The kms-key-arn is for encrypting sensitive data associated with the schedule if needed. Finally, state ENABLED activates the schedule.

The RoleArn needs specific permissions: it must have ecs:RunTask and iam:PassRole actions allowed. The PassRole permission is necessary because the ECS task itself will likely assume another IAM role to perform its actual work (e.g., S3 access, database writes), and EventBridge needs permission to "pass" that role to the ECS RunTask API call.

If your ECS task definition uses Fargate and requires specific subnets, ensure those subnets have sufficient available IP addresses. The AssignPublicIp setting is common for Fargate tasks that need to pull Docker images from ECR or access external services directly.

The Input JSON is particularly powerful. Your container’s entrypoint script can read this JSON and act accordingly. For example, if you had multiple scheduled tasks using the same task definition, you could differentiate their behavior via this input.

This approach contrasts with the older method of using EventBridge Rules with an ECS target. EventBridge Scheduler offers more granular control over scheduling, including time windows, retries, and dead-letter queues directly within the scheduler itself, rather than relying solely on ECS or Lambda for those capabilities.

The next thing you’ll likely encounter is needing to monitor these scheduled tasks.

Want structured learning?

Take the full Eventbridge course →