AWS for DevOps — Serverless Practice Exercises

4 minute read

9.6 — Serverless Practice Exercises


Exercise 1 — Lambda Configuration

A Lambda function processes images uploaded to S3. It resizes images and takes about 45 seconds per image. The function has these settings:

  • Memory: 128 MB
  • Timeout: 3 seconds
  • No dead letter queue

What problems will this cause? Fix the configuration.

Show Answer

Problems:

  1. Timeout too short — Image processing takes ~45 seconds but timeout is 3 seconds. The function will be killed every time.
  2. Memory too low — Image processing is CPU-intensive. Since Lambda CPU scales with memory, 128 MB gives minimal CPU. The function will be slow.
  3. No DLQ — S3 events are asynchronous. If the function fails, AWS retries twice then discards the event. Without a DLQ, failed images are lost.

Fixed configuration:

$ aws lambda update-function-configuration \
    --function-name resize-image \
    --timeout 120 \
    --memory-size 1024 \
    --dead-letter-config TargetArn=arn:aws:sqs:ap-south-1:123456789012:failed-resizes-dlq
  • Timeout: 120 seconds (45s average + buffer for large images)
  • Memory: 1024 MB (8× more CPU for image processing)
  • DLQ configured (failed events go to SQS for investigation)

Exercise 2 — API Design

A team wants to build a REST API with these endpoints:

Endpoint Method Description
/users GET List all users
/users POST Create a user
/users/{id} GET Get one user

They expect ~100 requests/minute during business hours and near-zero at night. Should they use REST API or HTTP API? Design the SAM template.

Show Answer

HTTP API — lower cost, lower latency, sufficient features for this use case.

AWSTemplateFormatVersion: "2010-09-09"
Transform: AWS::Serverless-2016-10-31

Globals:
  Function:
    Runtime: python3.12
    Timeout: 10
    MemorySize: 256

Resources:
  ListUsersFunction:
    Type: AWS::Serverless::Function
    Properties:
      Handler: app.list_users
      CodeUri: src/users/
      Policies:
        - DynamoDBReadPolicy:
            TableName: !Ref UsersTable
      Events:
        Api:
          Type: HttpApi
          Properties:
            Path: /users
            Method: get

  CreateUserFunction:
    Type: AWS::Serverless::Function
    Properties:
      Handler: app.create_user
      CodeUri: src/users/
      Policies:
        - DynamoDBCrudPolicy:
            TableName: !Ref UsersTable
      Events:
        Api:
          Type: HttpApi
          Properties:
            Path: /users
            Method: post

  GetUserFunction:
    Type: AWS::Serverless::Function
    Properties:
      Handler: app.get_user
      CodeUri: src/users/
      Policies:
        - DynamoDBReadPolicy:
            TableName: !Ref UsersTable
      Events:
        Api:
          Type: HttpApi
          Properties:
            Path: /users/{id}
            Method: get

  UsersTable:
    Type: AWS::Serverless::SimpleTable
    Properties:
      PrimaryKey:
        Name: UserId
        Type: String

Exercise 3 — Event Flow Debugging

A file is uploaded to S3, which triggers a Lambda. The Lambda should write a record to DynamoDB. But the DynamoDB table remains empty. CloudWatch Logs show:

[ERROR] ClientError: An error occurred (AccessDeniedException) when calling the PutItem operation

The Lambda’s execution role has s3:GetObject permission. What is missing?

Show Answer

Missing: DynamoDB permissions on the Lambda execution role.

The execution role has s3:GetObject (to read the uploaded file) but no DynamoDB permissions. The function needs dynamodb:PutItem to write to the table.

Fix:

{
    "Effect": "Allow",
    "Action": [
        "dynamodb:PutItem"
    ],
    "Resource": "arn:aws:dynamodb:ap-south-1:123456789012:table/MyTable"
}

Or with SAM:

Policies:
  - S3ReadPolicy:
      BucketName: !Ref UploadBucket
  - DynamoDBCrudPolicy:
      TableName: !Ref MyTable

Exercise 4 — SQS + Lambda Sizing

An SQS queue receives ~1,000 messages per minute. Each message takes ~2 seconds to process. The Lambda has:

  • Timeout: 30 seconds
  • Batch size: 10
  • Reserved concurrency: 5

Will this configuration keep up? Calculate the throughput.

Show Answer

Calculation:

  • Each invocation processes 10 messages in ~20 seconds (10 × 2s, assuming sequential)
  • Each of 5 concurrent Lambdas can do: 60s ÷ 20s = 3 invocations/min
  • Total: 5 × 3 × 10 = 150 messages/minute

Problem: The queue receives 1,000 messages/minute but only 150 are processed. The queue will grow indefinitely.

Fixes (choose one or combine):

  1. Increase concurrency: Set reserved concurrency to 50 (50 × 30 = 1,500 msg/min)
  2. Increase batch size: Set to 100 if messages are small (fewer invocations needed)
  3. Process messages in parallel within Lambda: Use async/threading to process the batch concurrently instead of sequentially
  4. Remove reserved concurrency limit: Let Lambda auto-scale to match demand

Exercise 5 — Design an Event-Driven Pipeline

Design a serverless pipeline for this workflow:

  1. A CSV file is uploaded to S3
  2. Parse the CSV and validate each row
  3. Valid rows → write to DynamoDB
  4. Invalid rows → send to an SQS dead letter queue
  5. After processing, send a summary email via SNS

Draw the architecture and list the AWS resources needed.

Show Answer

Architecture:

  S3 (upload bucket)
       │
       ▼ (S3 event: ObjectCreated, suffix=.csv)
  Lambda: parse-csv
       │
       ├── Valid rows ──▶ DynamoDB: Records table
       │
       ├── Invalid rows ──▶ SQS: invalid-rows-dlq
       │
       └── Summary ──▶ SNS: processing-complete
                          │
                          ▼
                        Email subscription

AWS Resources:

  1. S3 Bucket — csv-uploads with event notification on *.csv
  2. Lambda Function — parse-csv
    • Triggered by S3 event
    • Reads CSV from S3, validates rows
    • Writes valid rows to DynamoDB
    • Sends invalid rows to SQS
    • Publishes summary to SNS
    • DLQ configured for Lambda failures
  3. DynamoDB Table — Records (PK=RecordId)
  4. SQS Queue — invalid-rows-dlq (for bad data investigation)
  5. SNS Topic — processing-complete with email subscription
  6. IAM Role — S3 read, DynamoDB write, SQS send, SNS publish
  7. Lambda DLQ — SQS queue for Lambda execution failures (separate from data DLQ)

Key design decisions:

  • Lambda DLQ handles function failures (code errors)
  • SQS invalid-rows queue handles data failures (bad CSV rows)
  • SNS sends a single summary email — not one per row

Next Chapter → Monitoring & Observability

Updated: