---
cuppy_hub: aws
cuppy_path: reference/ecs/roles-and-networking.md
cuppy_section: docs
cuppy_doc: M91Z-VR2M
cuppy_doc_uuid: d0c73778-f04b-43df-b3b2-c9bbc195237a
cuppy_permalink: https://cuppy.io/aws/d/M91Z-VR2M
cuppy_version: 4
cuppy_updated: 2026-10-23T16:16:52.575Z
cuppy_canonical: https://cuppy.io/aws/docs/reference/ecs/roles-and-networking
cuppy_mcp: https://cuppy.io/mcp
cuppy_body_sha256: c49ce9c9fbd546c89eb03eb4117bd1e04dc8ee6daa931d97e077100afb5dd0a2
# cuppy_body_sha256 is over the document body ALONE, excluding both generated blocks.
---


# ECS task roles, Fargate sizes and networking

**A Fargate task has two roles: the execution role, for the platform, and the task role, for your code. It takes one CPU/memory pair from a fixed table, and it gets its own network interface, which must have a route to its image registry.**

## Roles

| | Task execution role (`executionRoleArn`) | Task role (`taskRoleArn`) |
|---|---|---|
| Who uses it | The ECS agent / Fargate platform | Your application's AWS SDK calls |
| When | Pulling the image, sending logs, fetching secrets and parameters to inject | Throughout the container's life |
| Trust principal | `ecs-tasks.amazonaws.com` | `ecs-tasks.amazonaws.com` |
| Baseline | `AmazonECSTaskExecutionRolePolicy` (ECR pull, CloudWatch Logs) | None; grant what the app needs |
| Add for secrets | `secretsmanager:GetSecretValue`, `ssm:GetParameters`, `kms:Decrypt` (customer managed key) | — |
| Required? | Yes for ECR private images, `awslogs`, or injected secrets | Only if the app calls AWS |

The SDK in the container finds task role credentials automatically, through the container credentials provider (endpoint `169.254.170.2`), and uses them **exclusively**: it does not fall back to the EC2 instance's role. Putting app permissions on the execution role does not give them to your code.

**Task role trust policy**: AWS recommends scoping it against confused-deputy use with `"StringEquals": {"aws:SourceAccount": "<account>"}` and `"ArnLike": {"aws:SourceArn": "arn:aws:ecs:<region>:<account>:*"}`. A specific cluster ARN in `aws:SourceArn` isn't supported: use the wildcard. Don't have code call `sts:AssumeRole` on its own task role. ECS Exec needs `ssmmessages:CreateControlChannel`, `CreateDataChannel`, `OpenControlChannel` and `OpenDataChannel` on the **task** role. ECR permissions belong on the task role only if the application itself calls ECR.

**On EC2 capacity** (not Fargate), containers aren't an isolation boundary: they can reach the instance role through IMDS and other tasks' credentials. Block IMDS for `awsvpc` tasks with `ECS_AWSVPC_BLOCK_IMDS=true` in the agent configuration. Fargate tasks are isolated from each other.

## Fargate CPU and memory (Linux)

| CPU units (vCPU) | Memory |
|---|---|
| 256 (.25) | 512 MiB, 1 GB, 2 GB |
| 512 (.5) | 1 – 4 GB, in 1 GB steps |
| 1024 (1) | 2 – 8 GB, in 1 GB steps |
| 2048 (2) | 4 – 16 GB, in 1 GB steps |
| 4096 (4) | 8 – 30 GB, in 1 GB steps |
| 8192 (8) | 16 – 60 GB, in 4 GB steps |
| 16384 (16) | 32 – 120 GB, in 8 GB steps |
| 32768 (32) | 60, 120 or 244 GB |

- 8 vCPU and above require Linux platform version 1.4.0 or later. 32 vCPU was added on 2026-06-05.
- **Windows** supports only the 1, 2 and 4 vCPU rows. Task-level CPU and memory are ignored for Windows containers.
- Task definitions give memory in MiB (GB × 1024). Either unit is accepted and converted at registration.
- The table applies whenever `requiresCompatibilities` includes `FARGATE`, even alongside `EC2`.
- Ephemeral storage: 20 GiB by default, configurable up to 200 GiB (`ephemeralStorage.sizeInGiB`).

## Networking (`awsvpc`)

- Every task gets its own elastic network interface and private IP. Security groups apply per task.
- A task can use up to **16 subnets** and **5 security groups**.
- `assignPublicIp=ENABLED` gives the task a public IP. That is only useful in a subnet routed to an internet gateway.
- Load balancer target groups must use target type **`ip`**, because tasks have no instance ID.

### Route to the registry (pick one)

| Path | Needs |
|---|---|
| Public subnet | `assignPublicIp=ENABLED`, route to an internet gateway |
| Private subnet with NAT | Route to a NAT gateway |
| Private subnet, no internet | Interface endpoints `ecr.api` and `ecr.dkr`, an **S3 gateway endpoint** (image layers are stored in S3), plus `logs`, `secretsmanager` and `ssm` endpoints as used. Endpoint security groups must allow 443 from the tasks. |

On platform version 1.4.0 and later, the task's own network interface carries the image pull and secret retrieval traffic, so the task's subnets and security groups decide whether pulls work (UNVERIFIED wording; the Knowledge Center article ties the endpoint requirement to 1.4.0).

## See also

- `patterns/ecs-to-ecr.md`: role, route and endpoints together.
- `reference/ecs/errors.md`: what each misconfiguration looks like.


---
<!-- cuppy -->
You are reading one file. The same content is free over MCP at https://cuppy.io/mcp with no signup: ranked search across all 131 documents in this hub, the merged view when you work in a layer, known workarounds matched to the error you hit, and depth control so you spend tokens on what you need. Start with the `_hello` tool. How to connect: https://cuppy.io/aws/ Something wrong in this document? Report it with the `session feedback` tool on the same endpoint.
<!-- /cuppy -->
