Elastic Container Service
Amazon Elastic Container Service (ECS) runs containers on AWS. The modern path is to push images to ECR, define an ECS task definition, and run that task through an ECS service on Fargate or EC2 capacity.
The older Docker ECS Compose context workflow is no longer the primary path for new deployments. Keep Compose for local development, then express the AWS deployment with ECS-native task definitions, AWS Copilot, AWS CDK, Terraform, CloudFormation, or the AWS CLI.
Deployment shape
The usual flow is:
Build the image with Docker Buildx.
Push the image to ECR.
Register an ECS task definition that references the ECR image.
Create or update an ECS service.
Watch logs in CloudWatch and deployments in ECS.
Task definition
The task definition is the unit ECS runs. This minimal Fargate example has one container and sends logs to CloudWatch.
1 {
2 "family": "student-rest",
3 "networkMode": "awsvpc",
4 "requiresCompatibilities": ["FARGATE"],
5 "cpu": "512",
6 "memory": "1024",
7 "executionRoleArn": "arn:aws:iam::<account-id>:role/ecsTaskExecutionRole",
8 "containerDefinitions": [
9 {
10 "name": "rest",
11 "image": "<account-id>.dkr.ecr.us-east-1.amazonaws.com/student-rest:<tag>",
12 "essential": true,
13 "portMappings": [
14 {
15 "containerPort": 8080,
16 "protocol": "tcp"
17 }
18 ],
19 "logConfiguration": {
20 "logDriver": "awslogs",
21 "options": {
22 "awslogs-group": "/ecs/student-rest",
23 "awslogs-region": "us-east-1",
24 "awslogs-stream-prefix": "ecs"
25 }
26 }
27 }
28 ]
29 }
Register the task definition.
1aws ecs register-task-definition --cli-input-json file://task-definition.json
Create a service
Create the ECS service on an existing cluster, subnet set, and security group. For internet-facing examples, the security group must allow the inbound application port and the subnets must match the public or load-balanced design.
1aws ecs create-service \
2 --cluster student-cluster \
3 --service-name student-rest \
4 --task-definition student-rest \
5 --desired-count 1 \
6 --launch-type FARGATE \
7 --network-configuration "awsvpcConfiguration={subnets=[subnet-abc123],securityGroups=[sg-abc123],assignPublicIp=ENABLED}"
Deploy a new image
When a new image is pushed, register a new task definition revision and update the service.
1aws ecs update-service \
2 --cluster student-cluster \
3 --service student-rest \
4 --task-definition student-rest \
5 --force-new-deployment
Watch rollout status.
1aws ecs describe-services \
2 --cluster student-cluster \
3 --services student-rest \
4 --query 'services[0].deployments'
Configuration and secrets
Do not put production secrets in the image or task definition plaintext.
Put non-secret configuration in environment variables.
Put secrets in AWS Secrets Manager or Systems Manager Parameter Store.
Grant the task role only the permissions the container needs.
Grant the task execution role permissions for ECR pulls and CloudWatch logs.
Use health checks and load balancer target groups for services that receive traffic.
Local Compose remains useful
Use Compose to run the same application locally. The local file should model service names, ports, volumes, environment variables, and health checks. The ECS definition should model AWS-specific concerns such as IAM roles, VPC networking, logs, autoscaling, deployment configuration, and load balancing.