AWS Deployment

Complete guide to deploying Pixashot on Amazon Web Services, including ECS/Fargate setup, monitoring, and AWS-specific optimizations.

This guide covers deploying Pixashot on Amazon Web Services (AWS) using various container services and best practices.

ECS vs Fargate Comparison

  • Serverless container management
  • No infrastructure to maintain
  • Automatic scaling
  • Pay-per-use pricing
  • Simplified security model

Amazon ECS with EC2

  • Full control over infrastructure
  • Custom instance types
  • Potentially lower costs at scale
  • Advanced networking options
  • Custom AMI support

Fargate Deployment

Prerequisites

# Install AWS CLI
curl "https://awscli.amazonaws.com/awscli-exe-linux-x86_64.zip" -o "awscliv2.zip"
unzip awscliv2.zip
sudo ./aws/install

# Configure AWS CLI
aws configure

Create Task Definition

{
  "family": "pixashot",
  "networkMode": "awsvpc",
  "requiresCompatibilities": ["FARGATE"],
  "cpu": "1024",
  "memory": "2048",
  "containerDefinitions": [
    {
      "name": "pixashot",
      "image": "gpriday/pixashot:latest",
      "portMappings": [
        {
          "containerPort": 8080,
          "protocol": "tcp"
        }
      ],
      "environment": [
        {
          "name": "AUTH_TOKEN",
          "value": "your_secret_token"
        },
        {
          "name": "WORKERS",
          "value": "4"
        },
        {
          "name": "MAX_REQUESTS",
          "value": "1000"
        }
      ],
      "healthCheck": {
        "command": ["CMD-SHELL", "curl -f http://localhost:8080/health/live || exit 1"],
        "interval": 30,
        "timeout": 5,
        "retries": 3,
        "startPeriod": 60
      },
      "logConfiguration": {
        "logDriver": "awslogs",
        "options": {
          "awslogs-group": "/ecs/pixashot",
          "awslogs-region": "us-west-2",
          "awslogs-stream-prefix": "ecs"
        }
      }
    }
  ]
}

Load Balancer Configuration

Application Load Balancer Setup

# Create ALB
aws elbv2 create-load-balancer \
  --name pixashot-alb \
  --subnets subnet-12345678 subnet-87654321 \
  --security-groups sg-12345678

# Create target group
aws elbv2 create-target-group \
  --name pixashot-tg \
  --protocol HTTP \
  --port 8080 \
  --vpc-id vpc-12345678 \
  --target-type ip \
  --health-check-path /health/live

# Create listener
aws elbv2 create-listener \
  --load-balancer-arn $ALB_ARN \
  --protocol HTTPS \
  --port 443 \
  --certificates CertificateArn=$CERT_ARN \
  --default-actions Type=forward,TargetGroupArn=$TG_ARN

Health Check Configuration

{
  "HealthCheckProtocol": "HTTP",
  "HealthCheckPort": "8080",
  "HealthCheckPath": "/health/live",
  "HealthCheckIntervalSeconds": 30,
  "HealthCheckTimeoutSeconds": 5,
  "HealthyThresholdCount": 2,
  "UnhealthyThresholdCount": 3
}

Auto Scaling Configuration

Service Auto Scaling

# Register scalable target
aws application-autoscaling register-scalable-target \
  --service-namespace ecs \
  --scalable-dimension ecs:service:DesiredCount \
  --resource-id service/pixashot-cluster/pixashot \
  --min-capacity 1 \
  --max-capacity 10

# Configure scaling policy
aws application-autoscaling put-scaling-policy \
  --policy-name pixashot-cpu-scaling \
  --service-namespace ecs \
  --scalable-dimension ecs:service:DesiredCount \
  --resource-id service/pixashot-cluster/pixashot \
  --policy-type TargetTrackingScaling \
  --target-tracking-scaling-policy-configuration '{
    "TargetValue": 70.0,
    "PredefinedMetricSpecification": {
      "PredefinedMetricType": "ECSServiceAverageCPUUtilization"
    }
  }'

CloudWatch Monitoring

Metric Collection

# Create log group
aws logs create-log-group --log-group-name /ecs/pixashot

# Create metric filter
aws logs put-metric-filter \
  --log-group-name /ecs/pixashot \
  --filter-name errors \
  --filter-pattern "ERROR" \
  --metric-transformations \
    metricName=ErrorCount,metricNamespace=Pixashot,metricValue=1

CloudWatch Alarms

# CPU utilization alarm
aws cloudwatch put-metric-alarm \
  --alarm-name pixashot-cpu-alarm \
  --alarm-description "CPU utilization exceeds 80%" \
  --metric-name CPUUtilization \
  --namespace AWS/ECS \
  --statistic Average \
  --period 300 \
  --threshold 80 \
  --comparison-operator GreaterThanThreshold \
  --evaluation-periods 2 \
  --alarm-actions $SNS_TOPIC_ARN

# Memory utilization alarm
aws cloudwatch put-metric-alarm \
  --alarm-name pixashot-memory-alarm \
  --alarm-description "Memory utilization exceeds 80%" \
  --metric-name MemoryUtilization \
  --namespace AWS/ECS \
  --statistic Average \
  --period 300 \
  --threshold 80 \
  --comparison-operator GreaterThanThreshold \
  --evaluation-periods 2 \
  --alarm-actions $SNS_TOPIC_ARN

# Error rate alarm
aws cloudwatch put-metric-alarm \
  --alarm-name pixashot-error-rate \
  --alarm-description "Error rate too high" \
  --metric-name ErrorCount \
  --namespace Pixashot \
  --statistic Sum \
  --period 300 \
  --threshold 10 \
  --comparison-operator GreaterThanThreshold \
  --evaluation-periods 2 \
  --alarm-actions $SNS_TOPIC_ARN

Dashboard Creation

aws cloudwatch put-dashboard \
  --dashboard-name "Pixashot-Dashboard" \
  --dashboard-body file://dashboard.json

Example dashboard.json:

{
    "widgets": [
        {
            "type": "metric",
            "properties": {
                "metrics": [
                    ["AWS/ECS", "CPUUtilization", "ServiceName", "pixashot"]
                ],
                "period": 300,
                "stat": "Average",
                "region": "us-west-2",
                "title": "CPU Utilization"
            }
        },
        {
            "type": "metric",
            "properties": {
                "metrics": [
                    ["AWS/ECS", "MemoryUtilization", "ServiceName", "pixashot"]
                ],
                "period": 300,
                "stat": "Average",
                "region": "us-west-2",
                "title": "Memory Utilization"
            }
        }
    ]
}

Cost Optimization

Resource Optimization

  1. Right-sizing Containers:
{
  "cpu": "1024",
  "memory": "2048",
  "requiresCompatibilities": ["FARGATE"]
}
  1. Spot Instances (for ECS EC2):
aws ecs create-capacity-provider \
  --name pixashot-spot \
  --auto-scaling-group-provider \
    "autoScalingGroupArn=$ASG_ARN,managedScaling={status=ENABLED,targetCapacity=100},managedTermination=true"

Cost Monitoring

# Create budget
aws budgets create-budget \
  --account-id $ACCOUNT_ID \
  --budget file://budget.json \
  --notifications-with-subscribers file://notifications.json

Example budget.json:

{
    "BudgetName": "Pixashot-Monthly",
    "BudgetLimit": {
        "Amount": "100",
        "Unit": "USD"
    },
    "TimeUnit": "MONTHLY",
    "BudgetType": "COST",
    "CostFilters": {
        "TagKeyValue": ["project:pixashot"]
    }
}

Security Configuration

IAM Roles

# Task execution role
aws iam create-role \
  --role-name pixashot-execution-role \
  --assume-role-policy-document file://task-execution-role.json

# Task role
aws iam create-role \
  --role-name pixashot-task-role \
  --assume-role-policy-document file://task-role.json

Example task-execution-role.json:

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Principal": {
                "Service": "ecs-tasks.amazonaws.com"
            },
            "Action": "sts:AssumeRole"
        }
    ]
}

Security Groups

# Create security group
aws ec2 create-security-group \
  --group-name pixashot-sg \
  --description "Security group for Pixashot containers"

# Configure inbound rules
aws ec2 authorize-security-group-ingress \
  --group-id $SG_ID \
  --protocol tcp \
  --port 8080 \
  --source $ALB_SG_ID

Infrastructure as Code

CloudFormation Template

AWSTemplateFormatVersion: '2010-09-09'
Description: 'Pixashot ECS Fargate Deployment'

Parameters:
  Environment:
    Type: String
    Default: production
    AllowedValues: [development, staging, production]

Resources:
  PixashotCluster:
    Type: AWS::ECS::Cluster
    Properties:
      ClusterName: !Sub pixashot-${Environment}
      CapacityProviders: [FARGATE]

  PixashotTaskDefinition:
    Type: AWS::ECS::TaskDefinition
    Properties:
      Family: pixashot
      Cpu: 1024
      Memory: 2048
      NetworkMode: awsvpc
      RequiresCompatibilities: [FARGATE]
      ExecutionRoleArn: !Ref TaskExecutionRole
      ContainerDefinitions:
        - Name: pixashot
          Image: gpriday/pixashot:latest
          PortMappings:
            - ContainerPort: 8080
          Environment:
            - Name: AUTH_TOKEN
              Value: !Sub '{{resolve:secretsmanager:${PixashotSecret}:SecretString:auth_token}}'
          HealthCheck:
            Command: ["CMD-SHELL", "curl -f http://localhost:8080/health/live || exit 1"]
            Interval: 30
            Timeout: 5
            Retries: 3
            StartPeriod: 60

Outputs:
  ClusterArn:
    Description: 'ECS Cluster ARN'
    Value: !GetAtt PixashotCluster.Arn

CDK Example

import * as cdk from 'aws-cdk-lib';
import * as ecs from 'aws-cdk-lib/aws-ecs';
import * as ecs_patterns from 'aws-cdk-lib/aws-ecs-patterns';

export class PixashotStack extends cdk.Stack {
  constructor(scope: cdk.App, id: string, props?: cdk.StackProps) {
    super(scope, id, props);

    const cluster = new ecs.Cluster(this, 'PixashotCluster', {
      vpc: new ec2.Vpc(this, 'PixashotVPC')
    });

    const loadBalancedService = new ecs_patterns.ApplicationLoadBalancedFargateService(this, 'PixashotService', {
      cluster,
      memoryLimitMiB: 2048,
      cpu: 1024,
      taskImageOptions: {
        image: ecs.ContainerImage.fromRegistry('gpriday/pixashot:latest'),
        environment: {
          AUTH_TOKEN: process.env.AUTH_TOKEN || '',
          WORKERS: '4',
          MAX_REQUESTS: '1000'
        },
        containerPort: 8080
      }
    });
  }
}
Get the Latest Updates