AWS for DevOps — Containers Practice Exercises

4 minute read

7.6 — Containers Practice Exercises

Test your understanding of ECS, ECR, task definitions, services, and ALB integration.


Exercise 1 — Fargate vs EC2

A team is evaluating launch types for these workloads. Recommend Fargate or EC2 for each:

# Workload
A A web API with variable traffic (5-500 requests/sec)
B A machine learning inference service that needs GPU
C A startup’s development environment (3 microservices)
D A company running 200 containers 24/7 with predictable load
Show Answer
# Recommendation Why
A Fargate Per-task scaling is perfect for variable traffic; no servers to manage
B EC2 Fargate doesn’t support GPUs; need GPU instances (p3, g4dn)
C Fargate (or Fargate Spot) Simplicity matters for small teams; Spot saves money in dev
D EC2 with Reserved Instances At scale with predictable load, EC2 Reserved is significantly cheaper than Fargate

Exercise 2 — Fix the Task Definition

This task definition fails to register with the error: “Invalid CPU or memory value”. Why?

{
  "family": "my-app",
  "requiresCompatibilities": ["FARGATE"],
  "networkMode": "awsvpc",
  "cpu": "256",
  "memory": "4096",
  "containerDefinitions": [
    {
      "name": "app",
      "image": "123456789012.dkr.ecr.ap-south-1.amazonaws.com/my-app:v1",
      "essential": true,
      "portMappings": [{ "containerPort": 8080 }]
    }
  ]
}
Show Answer

Problem: Invalid CPU/memory combination.

cpu=256 (0.25 vCPU) only supports memory values of 512, 1024, or 2048 (0.5, 1, or 2 GB). memory=4096 (4 GB) is not a valid option for 0.25 vCPU.

Fix: Either:

  • Increase CPU: "cpu": "512" (0.5 vCPU supports up to 4 GB)
  • Or decrease memory: "memory": "2048" (2 GB fits with 0.25 vCPU)

Always check the Fargate CPU/memory combination table before registering task definitions.


Exercise 3 — IAM Role Confusion

A developer’s ECS task can pull its image from ECR and write logs to CloudWatch, but the application code inside the container gets AccessDenied when trying to read from an S3 bucket. The execution role has s3:GetObject permission. What is wrong?

Show Answer

Problem: The S3 permission is on the Execution Role instead of the Task Role.

  • Execution Role = permissions for the ECS agent (pull images, write logs, read secrets)
  • Task Role = permissions for your application code (S3, DynamoDB, SQS, etc.)

The ECS agent doesn’t use S3 for your business logic — your app code does. Move the s3:GetObject permission to the Task Role (taskRoleArn in the task definition).

Key rule: If your application code needs to call an AWS service, add the permission to the Task Role. If the ECS infrastructure needs it (images, logs, secrets), add it to the Execution Role.


Exercise 4 — ECR Lifecycle Design

A team pushes 5-10 Docker images per day to ECR. After 6 months, they have 1,200 images and their ECR storage costs are growing. Design a lifecycle policy that:

  1. Keeps the last 20 tagged images (tags like v1.0.1, v1.0.2)
  2. Removes untagged images older than 3 days
  3. Keeps all images tagged with release-* indefinitely
Show Answer
{
  "rules": [
    {
      "rulePriority": 1,
      "description": "Keep all release images forever",
      "selection": {
        "tagStatus": "tagged",
        "tagPrefixList": ["release-"],
        "countType": "imageCountMoreThan",
        "countNumber": 9999
      },
      "action": { "type": "expire" }
    },
    {
      "rulePriority": 2,
      "description": "Keep only last 20 version-tagged images",
      "selection": {
        "tagStatus": "tagged",
        "tagPrefixList": ["v"],
        "countType": "imageCountMoreThan",
        "countNumber": 20
      },
      "action": { "type": "expire" }
    },
    {
      "rulePriority": 3,
      "description": "Remove untagged images after 3 days",
      "selection": {
        "tagStatus": "untagged",
        "countType": "sinceImagePushed",
        "countUnit": "days",
        "countNumber": 3
      },
      "action": { "type": "expire" }
    }
  ]
}

Key points:

  • Rules are evaluated in priority order — lower number = higher priority
  • Rule 1 (priority 1) protects release-* images by setting an unreachable threshold
  • Rule 2 keeps only the most recent 20 v* images
  • Rule 3 cleans up dangling untagged images quickly

Exercise 5 — ECS + ALB Architecture

Design the architecture for a microservices application with these requirements:

  • Two services: api (REST API) and web (frontend)
  • Single ALB with path-based routing: /api/* → api service, /* → web service
  • Both services on Fargate in private subnets
  • Auto-scaling: API scales on request count, Web scales on CPU

List the AWS resources needed and the key configuration for each.

Show Answer

Resources needed:

  1. VPC with 2 public subnets (ALB) + 2 private subnets (tasks)
  2. NAT Gateway in public subnet (tasks need internet for ECR pulls)
  3. ALB in public subnets, internet-facing
  4. Two Target Groups:
    • api-tg: target-type=ip, port=8080, health-check=/api/health
    • web-tg: target-type=ip, port=3000, health-check=/health
  5. Listener on port 80 (or 443 with ACM certificate):
    • Rule priority 10: path-pattern /api/* → api-tg
    • Default action → web-tg
  6. ECS Cluster: production
  7. Two Task Definitions:
    • api:1 — cpu=512, memory=1024, port=8080
    • web:1 — cpu=256, memory=512, port=3000
  8. Two ECS Services:
    • api — desired=3, load-balancer=api-tg, health-check-grace=120s
    • web — desired=2, load-balancer=web-tg, health-check-grace=60s
  9. Two ECR Repositories: api, web
  10. Security Groups:
    • sg-alb: inbound 80/443 from 0.0.0.0
    • sg-api-tasks: inbound 8080 from sg-alb only
    • sg-web-tasks: inbound 3000 from sg-alb only
  11. Auto-scaling:
    • API: TargetTrackingScaling with ALBRequestCountPerTarget, target=500
    • Web: TargetTrackingScaling with ECSServiceAverageCPUUtilization, target=70%
  12. IAM Roles: Execution role (ECR + Logs), Task roles (one per service)

Next Chapter → Infrastructure as Code

Updated: