AWS for DevOps — ECS: Fargate vs EC2

3 minute read

7.1 — ECS: Fargate vs EC2 Launch Types

Amazon Elastic Container Service (ECS) is AWS’s container orchestrator. When you run containers on ECS, you choose a launch type — this determines who manages the underlying compute.

The Two Launch Types

  ECS Cluster
  ┌──────────────────────────────────────┐
  │                                       │
  │  Fargate Launch Type                  │
  │  ┌────────┐ ┌────────┐ ┌────────┐   │
  │  │ Task A │ │ Task B │ │ Task C │   │
  │  │(0.5 CPU│ │(1 CPU  │ │(2 CPU  │   │
  │  │ 1GB)   │ │ 2GB)   │ │ 4GB)   │   │
  │  └────────┘ └────────┘ └────────┘   │
  │  AWS manages the servers ▲           │
  │                                       │
  │  EC2 Launch Type                      │
  │  ┌─── EC2 Instance ───┐              │
  │  │ ┌──────┐ ┌──────┐  │ ┌─── EC2 ──┐│
  │  │ │Task D│ │Task E│  │ │ ┌──────┐ ││
  │  │ └──────┘ └──────┘  │ │ │Task F│ ││
  │  │   You manage this ▲ │ │ └──────┘ ││
  │  └────────────────────┘ └──────────┘│
  └──────────────────────────────────────┘

Comparison

Aspect Fargate EC2
Server management None — AWS handles it You manage EC2 instances
Scaling Per-task (instant) Scale instances + tasks
Pricing Per vCPU/GB per second EC2 instance cost (can use Reserved/Spot)
Cost at scale More expensive Cheaper with Reserved Instances
GPU support No Yes
Docker-in-Docker No Yes (privileged mode)
EBS volumes No (EFS only) Yes
SSH into container host No Yes
Startup time ~30-60 seconds Faster (instances already running)
Best for Most workloads, teams wanting simplicity GPU workloads, cost optimisation at scale

Creating an ECS Cluster

# Fargate-only cluster (no EC2 instances to manage)
$ aws ecs create-cluster --cluster-name my-app-cluster
{
    "cluster": {
        "clusterArn": "arn:aws:ecs:ap-south-1:123456789012:cluster/my-app-cluster",
        "clusterName": "my-app-cluster",
        "status": "ACTIVE"
    }
}

# Cluster with EC2 capacity provider
$ aws ecs create-cluster \
    --cluster-name my-ec2-cluster \
    --capacity-providers FARGATE FARGATE_SPOT \
    --default-capacity-provider-strategy \
        capacityProvider=FARGATE,weight=1 \
        capacityProvider=FARGATE_SPOT,weight=3

Capacity Providers

Capacity providers control where tasks run and how they scale:

Provider Description Use Case
FARGATE Standard Fargate Production workloads
FARGATE_SPOT Spot pricing (up to 70% cheaper) Fault-tolerant tasks (batch, dev)
EC2 Auto Scaling Group Your own instances GPU, cost optimisation
# Mix Fargate and Fargate Spot (75% Spot, 25% On-Demand)
$ aws ecs put-cluster-capacity-providers \
    --cluster my-app-cluster \
    --capacity-providers FARGATE FARGATE_SPOT \
    --default-capacity-provider-strategy \
        capacityProvider=FARGATE,weight=1,base=1 \
        capacityProvider=FARGATE_SPOT,weight=3

The base=1 ensures at least 1 task always runs on standard Fargate (reliable), while additional tasks prefer Spot (cheaper).

When to Choose What

  "I just want to run containers"
       │
    Fargate
       │
  "I need GPUs / Docker-in-Docker / SSH access"
       │
    EC2
       │
  "I want cheaper Fargate for non-critical tasks"
       │
    Fargate Spot
       │
  "I have 100+ containers and want to save money"
       │
    EC2 with Reserved Instances
       │
  "I already use Kubernetes"
       │
    EKS (not ECS)

Real-World Example

A typical production setup:

# Production: Standard Fargate (reliable)
$ aws ecs create-service \
    --cluster production \
    --service-name api \
    --launch-type FARGATE \
    --task-definition api:5 \
    --desired-count 3

# Development: Fargate Spot (cost-effective)
$ aws ecs create-service \
    --cluster development \
    --service-name api \
    --capacity-provider-strategy \
        capacityProvider=FARGATE_SPOT,weight=1 \
    --task-definition api:5 \
    --desired-count 1

Common Mistakes

Mistake Why It Hurts Fix
Using Fargate for GPU workloads Fargate doesn’t support GPUs Use EC2 launch type with GPU instances
Fargate Spot for critical prod services Tasks can be interrupted Use standard Fargate for production
Over-provisioning Fargate tasks Paying for unused CPU/memory Right-size using Container Insights metrics
Not using capacity providers Stuck on one launch type Configure mixed strategies

Quick Reference

Task Command
Create cluster aws ecs create-cluster --cluster-name NAME
List clusters aws ecs list-clusters
Describe cluster aws ecs describe-clusters --clusters NAME
Delete cluster aws ecs delete-cluster --cluster NAME
Set capacity providers aws ecs put-cluster-capacity-providers --cluster NAME ...

Next → ECR — Elastic Container Registry

Updated: