DEV Community

Cover image for πŸš€ Multi-Application CI/CD on AWS (Production-Style)
Mubeen Babar
Mubeen Babar

Posted on

πŸš€ Multi-Application CI/CD on AWS (Production-Style)

🎯 Project Goal
Host multiple web applications on AWS where:

  • Developers push code to GitHub
  • GitHub Actions automatically:
  • Tests code
  • Builds Docker images
  • Pushes images to AWS ECR
  • Deploys to AWS ECS (Fargate) or EC2 + Docker
  • End users access apps via HTTPS (ALB + ACM)
  • Logs & monitoring via CloudWatch
  • Supports rolling / blue-green deployment

πŸ—οΈ High-Level Architecture

Developer
   |
   v
GitHub Repo (App1, App2, App3)
   |
GitHub Actions (CI/CD)
   |
   |-- Test
   |-- Docker Build
   |-- Push to ECR
   v
AWS ECR (Images)
   |
AWS ECS (Fargate)
   |
Application Load Balancer
   |
   v
End Users (HTTPS)
Enter fullscreen mode Exit fullscreen mode

πŸ“ Repository Structure

multi-app-devops/
β”œβ”€β”€ app1/
β”‚   β”œβ”€β”€ Dockerfile
β”‚   └── src/
β”œβ”€β”€ app2/
β”‚   β”œβ”€β”€ Dockerfile
β”‚   └── src/
β”œβ”€β”€ app3/
β”‚   β”œβ”€β”€ Dockerfile
β”‚   └── src/
└── .github/
    └── workflows/
        └── deploy.yml
Enter fullscreen mode Exit fullscreen mode

Each app is independent but deployed via same pipeline logic.

πŸ” STEP 1: AWS ACCOUNT & IAM
Create IAM User (DevOpsUser)
Permissions:

  • AmazonEC2FullAccess
  • AmazonECS_FullAccess
  • AmazonEC2ContainerRegistryFullAccess
  • CloudWatchFullAccess
  • IAMReadOnlyAccess

⚠️ Create Access Key (Programmatic)

🌐 STEP 2: Networking (VPC)

  • Create VPC
  • 2 Public Subnets
  • Internet Gateway
  • Route Table
  • Security Groups:
  • ALB: 80, 443
  • ECS: 3000/5000/80 (app ports)

πŸ“¦ STEP 3: Create ECR Repositories
Create one ECR per app:

app1-ecr
app2-ecr
app3-ecr
Enter fullscreen mode Exit fullscreen mode

Save:

  • AWS Account ID
  • Region
  • Repository URI Example:
123456789012.dkr.ecr.us-east-1.amazonaws.com/app1
Enter fullscreen mode Exit fullscreen mode

🐳 STEP 4: Dockerize Applications
Example Dockerfile (Node.js / Python)

FROM node:18-alpine
WORKDIR /app
COPY package*.json .
RUN npm install
COPY . .
EXPOSE 3000
CMD ["npm", "start"]
Enter fullscreen mode Exit fullscreen mode

Repeat per app.

βš™οΈ STEP 5: ECS Cluster (Fargate)

  1. Create ECS Cluster
  2. Create Task Definition per App
  • Container Image: ECR URI
  • Port Mapping
  • CPU & Memory

Create Service

  • Launch Type: FARGATE
  • Attach ALB
  • Desired Tasks: 2 (HA)

🌍 STEP 6: Application Load Balancer
Create ALB
Listener:
HTTP β†’ Redirect HTTPS
HTTPS β†’ Target Groups
Path-based routing:

/app1 β†’ app1-service
/app2 β†’ app2-service
/app3 β†’ app3-service
Enter fullscreen mode Exit fullscreen mode

πŸ”‘ STEP 7: GitHub Secrets
In GitHub Repo β†’ Settings β†’ Secrets
AWS_ACCESS_KEY_ID
AWS_SECRET_ACCESS_KEY
AWS_REGION
AWS_ACCOUNT_ID
ECR_REPO_APP1
ECR_REPO_APP2

πŸ”„ STEP 8: GitHub Actions CI/CD Pipeline
.github/workflows/deploy.yml

name: CI-CD Pipeline

on:
  push:
    branches: [ "main" ]

env:
  AWS_REGION: us-east-1

jobs:
  deploy:
    runs-on: ubuntu-latest

    steps:
    - name: Checkout Code
      uses: actions/checkout@v4

    - name: Configure AWS Credentials
      uses: aws-actions/configure-aws-credentials@v4
      with:
        aws-access-key-id: ${{ secrets.AWS_ACCESS_KEY_ID }}
        aws-secret-access-key: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
        aws-region: ${{ env.AWS_REGION }}

    - name: Login to Amazon ECR
      run: |
        aws ecr get-login-password --region $AWS_REGION \
        | docker login --username AWS --password-stdin \
        ${{ secrets.AWS_ACCOUNT_ID }}.dkr.ecr.$AWS_REGION.amazonaws.com

    - name: Build & Push App1
      run: |
        docker build -t app1 ./app1
        docker tag app1:latest ${{ secrets.ECR_REPO_APP1 }}:latest
        docker push ${{ secrets.ECR_REPO_APP1 }}:latest

    - name: Deploy to ECS
      run: |
        aws ecs update-service \
          --cluster devops-cluster \
          --service app1-service \
          --force-new-deployment

Enter fullscreen mode Exit fullscreen mode

βœ” Repeat build steps for app2 & app3.

πŸ“Š STEP 9: Monitoring & Logs
Enable CloudWatch Logs in ECS Task Definition
View:

  • App logs
  • CPU/Memory
  • Health checks

πŸ” STEP 10: Security & Best Practices
βœ” HTTPS using ACM
βœ” IAM least privilege
βœ” Secrets in GitHub (not code)
βœ” Private ECR
βœ” Auto-scaling

πŸ§ͺ STEP 11: Testing Flow

  1. Developer changes code
  2. Push to main
  3. GitHub Action triggers
  4. Docker image rebuilt
  5. Image pushed to ECR
  6. ECS pulls new image
  7. Rolling deployment
  8. End user sees updated app

Top comments (0)