Technology

CircleCI Orbs High Availability HA Setup

circleci orbs high availability ha setup
CircleCI Orbs High Availability HA Setup | SiamCafe Blog
2025-06-02· อ. บอม — SiamCafe.net· 1,623 คำ

CircleCI Orbs High Availability HA Setup คืออะไร

CircleCI เป็น CI/CD platform ยอดนิยมที่รองรับ automated build, test และ deploy CircleCI Orbs คือ reusable configuration packages ที่ช่วยลด boilerplate config และแชร์ best practices ข้าม projects High Availability (HA) Setup คือการออกแบบระบบให้มี uptime สูงสุด (99.9%+) โดยไม่มี single point of failure การรวมแนวคิดเหล่านี้ช่วยให้ CI/CD pipeline มีความเสถียร deploy applications ที่มี HA architecture และใช้ Orbs จัดการ infrastructure อย่างมีประสิทธิภาพ

CircleCI Orbs พื้นฐาน

# orbs_basics.py — CircleCI Orbs fundamentals
import json

class CircleCIOrbs:
    CONCEPTS = {
        "orb": {
            "name": "Orb",
            "description": "Reusable package ของ CircleCI config (commands, jobs, executors)",
            "registry": "circleci.com/developer/orbs (public registry)",
        },
        "command": {
            "name": "Command",
            "description": "Reusable step sequence ที่ใช้ใน jobs",
            "example": "aws-cli/setup — ติดตั้งและ configure AWS CLI",
        },
        "job": {
            "name": "Job",
            "description": "Pre-defined job ที่พร้อมใช้ใน workflow",
            "example": "docker/publish — build + push Docker image",
        },
        "executor": {
            "name": "Executor",
            "description": "Pre-configured execution environment",
            "example": "node/default — Node.js environment พร้อมใช้",
        },
    }

    POPULAR_ORBS = {
        "aws-cli": {"name": "aws-cli", "use": "AWS CLI setup and commands", "installs": "2B+"},
        "docker": {"name": "docker", "use": "Build, tag, push Docker images", "installs": "500M+"},
        "kubernetes": {"name": "kubernetes", "use": "Deploy to Kubernetes clusters", "installs": "100M+"},
        "slack": {"name": "slack", "use": "Send notifications to Slack", "installs": "300M+"},
        "terraform": {"name": "terraform", "use": "Terraform plan and apply", "installs": "200M+"},
        "node": {"name": "node", "use": "Node.js environment and caching", "installs": "400M+"},
    }

    BASIC_CONFIG = """
# .circleci/config.yml — Basic Orbs usage
version: 2.1

orbs:
  aws-cli: circleci/aws-cli@4.1
  docker: circleci/docker@2.6
  slack: circleci/slack@4.13

jobs:
  build-and-test:
    docker:
      - image: cimg/python:3.11
    steps:
      - checkout
      - run: pip install -r requirements.txt
      - run: pytest tests/ -v
      - slack/notify:
          event: fail
          template: basic_fail_1

  deploy:
    docker:
      - image: cimg/python:3.11
    steps:
      - checkout
      - aws-cli/setup
      - docker/build:
          image: myapp
          tag: 
      - docker/push:
          image: myapp
          tag: 

workflows:
  build-deploy:
    jobs:
      - build-and-test
      - deploy:
          requires: [build-and-test]
          filters:
            branches:
              only: main
"""

    def show_concepts(self):
        print("=== Orbs Concepts ===\n")
        for key, concept in self.CONCEPTS.items():
            print(f"[{concept['name']}] {concept['description']}")

    def show_popular(self):
        print(f"\n=== Popular Orbs ===")
        for key, orb in self.POPULAR_ORBS.items():
            print(f"  [{orb['name']}] {orb['use']}")

    def show_config(self):
        print(f"\n=== Basic Config ===")
        print(self.BASIC_CONFIG[:500])

orbs = CircleCIOrbs()
orbs.show_concepts()
orbs.show_popular()
orbs.show_config()

HA Architecture Patterns

# ha_patterns.py — High Availability architecture patterns
import json

class HAPatterns:
    PATTERNS = {
        "active_active": {
            "name": "Active-Active",
            "description": "ทุก instance รับ traffic พร้อมกัน load balanced",
            "use": "Web servers, API gateways, stateless services",
            "uptime": "99.99%+",
            "complexity": "Medium-High",
        },
        "active_passive": {
            "name": "Active-Passive (Failover)",
            "description": "Primary instance ทำงาน, secondary standby พร้อม takeover",
            "use": "Databases, stateful services",
            "uptime": "99.9%+",
            "complexity": "Medium",
        },
        "multi_az": {
            "name": "Multi-AZ (Availability Zone)",
            "description": "Deploy ข้าม AZ ใน region เดียว",
            "use": "Cloud workloads (AWS, GCP, Azure)",
            "uptime": "99.99%",
            "complexity": "Medium",
        },
        "multi_region": {
            "name": "Multi-Region",
            "description": "Deploy ข้าม regions (geographic redundancy)",
            "use": "Global applications, disaster recovery",
            "uptime": "99.999%",
            "complexity": "High",
        },
    }

    HA_COMPONENTS = {
        "load_balancer": "ALB/NLB, Nginx, HAProxy — กระจาย traffic",
        "auto_scaling": "EC2 ASG, K8s HPA — scale ตาม load",
        "database_ha": "RDS Multi-AZ, Aurora, PostgreSQL streaming replication",
        "cache_ha": "Redis Sentinel/Cluster, ElastiCache Multi-AZ",
        "dns_failover": "Route53 health checks, Cloudflare load balancing",
        "monitoring": "CloudWatch, Prometheus, PagerDuty — detect failures",
    }

    def show_patterns(self):
        print("=== HA Patterns ===\n")
        for key, pattern in self.PATTERNS.items():
            print(f"[{pattern['name']}] {pattern['description']}")
            print(f"  Use: {pattern['use']} | Uptime: {pattern['uptime']}")
            print()

    def show_components(self):
        print("=== HA Components ===")
        for comp, desc in self.HA_COMPONENTS.items():
            print(f"  [{comp}] {desc}")

ha = HAPatterns()
ha.show_patterns()
ha.show_components()

CircleCI HA Deployment Pipeline

# ha_pipeline.py — HA deployment with CircleCI
import json

class HAPipeline:
    CONFIG = """
# .circleci/config.yml — HA Deployment Pipeline
version: 2.1

orbs:
  aws-cli: circleci/aws-cli@4.1
  aws-ecs: circleci/aws-ecs@4.0
  kubernetes: circleci/kubernetes@1.3
  slack: circleci/slack@4.13
  rollbar: circleci/rollbar@1.0

executors:
  deploy-executor:
    docker:
      - image: cimg/python:3.11
    environment:
      AWS_REGION: ap-southeast-1

jobs:
  test:
    docker:
      - image: cimg/python:3.11
      - image: cimg/postgres:15.0
    steps:
      - checkout
      - restore_cache:
          keys: [deps-{{ checksum "requirements.txt" }}]
      - run: pip install -r requirements.txt
      - save_cache:
          key: deps-{{ checksum "requirements.txt" }}
          paths: [~/.cache/pip]
      - run: pytest tests/ -v --junitxml=results.xml
      - store_test_results:
          path: results.xml

  build-image:
    executor: deploy-executor
    steps:
      - checkout
      - setup_remote_docker:
          version: 20.10.24
      - run:
          name: Build and push to ECR
          command: |
            aws ecr get-login-password | docker login --username AWS --password-stdin $ECR_URL
            docker build -t $ECR_URL/myapp: .
            docker push $ECR_URL/myapp:

  deploy-blue-green:
    executor: deploy-executor
    steps:
      - aws-cli/setup
      - run:
          name: Blue-Green Deploy to ECS
          command: |
            # Update task definition with new image
            aws ecs update-service \\
              --cluster production \\
              --service myapp-green \\
              --task-definition myapp: \\
              --desired-count 3
            
            # Wait for green deployment stable
            aws ecs wait services-stable \\
              --cluster production \\
              --services myapp-green
            
            # Switch ALB target group
            aws elbv2 modify-listener \\
              --listener-arn $LISTENER_ARN \\
              --default-actions Type=forward, TargetGroupArn=$GREEN_TG_ARN
      - slack/notify:
          event: pass
          template: success_tagged_deploy_1

  health-check:
    executor: deploy-executor
    steps:
      - run:
          name: Post-deploy health check
          command: |
            for i in $(seq 1 10); do
              STATUS=$(curl -s -o /dev/null -w "%{http_code}" https://api.example.com/health)
              if [ "$STATUS" = "200" ]; then
                echo "Health check passed"
                exit 0
              fi
              sleep 10
            done
            echo "Health check failed"
            exit 1

workflows:
  ha-deploy:
    jobs:
      - test
      - build-image:
          requires: [test]
          filters:
            branches:
              only: main
      - deploy-blue-green:
          requires: [build-image]
      - health-check:
          requires: [deploy-blue-green]
"""

    def show_config(self):
        print("=== HA Pipeline Config ===")
        print(self.CONFIG[:800])

    def deployment_strategies(self):
        print(f"\n=== Deployment Strategies for HA ===")
        strategies = [
            {"name": "Blue-Green", "downtime": "Zero", "rollback": "Instant (switch back)", "complexity": "Medium"},
            {"name": "Canary", "downtime": "Zero", "rollback": "Fast (route back)", "complexity": "High"},
            {"name": "Rolling Update", "downtime": "Near-zero", "rollback": "Slow (redeploy)", "complexity": "Low"},
            {"name": "A/B Testing", "downtime": "Zero", "rollback": "Instant", "complexity": "High"},
        ]
        for s in strategies:
            print(f"  [{s['name']}] Downtime: {s['downtime']} | Rollback: {s['rollback']}")

pipeline = HAPipeline()
pipeline.show_config()
pipeline.deployment_strategies()

Infrastructure as Code for HA

# iac_ha.py — Terraform HA infrastructure
import json

class IACHA:
    TERRAFORM = """
# main.tf — HA infrastructure with Terraform
provider "aws" {
  region = "ap-southeast-1"
}

# VPC with Multi-AZ
module "vpc" {
  source  = "terraform-aws-modules/vpc/aws"
  version = "5.0"
  
  name = "ha-vpc"
  cidr = "10.0.0.0/16"
  
  azs             = ["ap-southeast-1a", "ap-southeast-1b", "ap-southeast-1c"]
  private_subnets = ["10.0.1.0/24", "10.0.2.0/24", "10.0.3.0/24"]
  public_subnets  = ["10.0.101.0/24", "10.0.102.0/24", "10.0.103.0/24"]
  
  enable_nat_gateway = true
  single_nat_gateway = false  # NAT per AZ for HA
}

# ALB (Application Load Balancer)
resource "aws_lb" "main" {
  name               = "ha-alb"
  internal           = false
  load_balancer_type = "application"
  subnets            = module.vpc.public_subnets
  
  enable_deletion_protection = true
  enable_cross_zone_load_balancing = true
}

# ECS Cluster with Fargate
resource "aws_ecs_cluster" "main" {
  name = "ha-cluster"
  
  setting {
    name  = "containerInsights"
    value = "enabled"
  }
}

# ECS Service (Multi-AZ)
resource "aws_ecs_service" "app" {
  name            = "myapp"
  cluster         = aws_ecs_cluster.main.id
  task_definition = aws_ecs_task_definition.app.arn
  desired_count   = 3  # Spread across 3 AZs
  launch_type     = "FARGATE"
  
  network_configuration {
    subnets         = module.vpc.private_subnets
    security_groups = [aws_security_group.app.id]
  }
  
  load_balancer {
    target_group_arn = aws_lb_target_group.app.arn
    container_name   = "myapp"
    container_port   = 8080
  }
}

# RDS Multi-AZ
resource "aws_db_instance" "main" {
  identifier     = "ha-postgres"
  engine         = "postgres"
  engine_version = "15"
  instance_class = "db.r6g.large"
  
  multi_az               = true
  storage_encrypted      = true
  backup_retention_period = 7
  
  db_subnet_group_name = aws_db_subnet_group.main.name
}
"""

    def show_terraform(self):
        print("=== Terraform HA Config ===")
        print(self.TERRAFORM[:700])

    def ha_checklist(self):
        print(f"\n=== HA Checklist ===")
        checks = [
            ("Multi-AZ deployment (3 AZs)", True),
            ("Load balancer health checks", True),
            ("Auto-scaling configured", True),
            ("Database Multi-AZ failover", True),
            ("Redis/Cache HA (Sentinel/Cluster)", True),
            ("DNS failover configured", True),
            ("Monitoring + alerting active", True),
            ("Disaster recovery plan documented", True),
            ("Runbook for failover scenarios", True),
        ]
        for name, status in checks:
            icon = "PASS" if status else "TODO"
            print(f"  [{icon:>4}] {name}")

iac = IACHA()
iac.show_terraform()
iac.ha_checklist()

Monitoring & Failover

# monitoring.py — HA monitoring and failover
import json
import random

class HAMonitoring:
    def cluster_status(self):
        print("=== HA Cluster Status ===\n")
        services = [
            {"name": "API Gateway (ALB)", "status": "healthy", "instances": "3/3", "az": "3 AZs"},
            {"name": "App Service (ECS)", "status": "healthy", "instances": "6/6", "az": "3 AZs"},
            {"name": "Database (RDS)", "status": "healthy", "instances": "Primary + Standby", "az": "Multi-AZ"},
            {"name": "Cache (Redis)", "status": "healthy", "instances": "3 nodes", "az": "3 AZs"},
            {"name": "CDN (CloudFront)", "status": "healthy", "instances": "Global", "az": "Edge locations"},
        ]
        for s in services:
            print(f"  [{s['status']:>7}] {s['name']:<25} Instances: {s['instances']}")

    def uptime_metrics(self):
        print(f"\n=== Uptime Metrics ===")
        metrics = {
            "Current uptime": f"{random.uniform(99.95, 99.99):.3f}%",
            "Last 30 days": f"{random.uniform(99.90, 99.99):.3f}%",
            "MTTR": f"{random.randint(1, 10)} minutes",
            "MTBF": f"{random.randint(30, 180)} days",
            "Incidents (30d)": f"{random.randint(0, 3)}",
            "RTO target": "< 5 minutes",
            "RPO target": "< 1 minute",
        }
        for m, v in metrics.items():
            print(f"  {m}: {v}")

    def failover_test(self):
        print(f"\n=== Failover Test Results ===")
        tests = [
            {"scenario": "Single instance failure", "recovery": f"{random.randint(5, 30)}s", "result": "PASS"},
            {"scenario": "AZ failure", "recovery": f"{random.randint(30, 120)}s", "result": "PASS"},
            {"scenario": "Database failover", "recovery": f"{random.randint(30, 90)}s", "result": "PASS"},
            {"scenario": "Region failover", "recovery": f"{random.randint(120, 600)}s", "result": "PASS"},
        ]
        for t in tests:
            print(f"  [{t['result']:>4}] {t['scenario']:<30} Recovery: {t['recovery']}")

mon = HAMonitoring()
mon.cluster_status()
mon.uptime_metrics()
mon.failover_test()

FAQ - คำถามที่พบบ่อย

Q: CircleCI Orbs กับ GitHub Actions reusable workflows อันไหนดี?

A: CircleCI Orbs: mature ecosystem, versioned packages, central registry, reusable across orgs GitHub Actions: larger marketplace, tighter GitHub integration, easier to start ใช้ CircleCI: ถ้าใช้ CircleCI อยู่แล้ว, ต้องการ versioned reusable configs ใช้ GitHub Actions: ถ้าใช้ GitHub, ต้องการ simplicity

Q: HA ต้องใช้ minimum กี่ AZs?

A: 2 AZs: minimum สำหรับ HA (ถ้า 1 AZ ล่ม ยังมี 1 AZ) 3 AZs: แนะนำ (quorum-based systems เช่น etcd, Consul ต้อง 3+) Cost: Multi-AZ เพิ่มค่าใช้จ่าย ~50-100% แต่คุ้มสำหรับ production

Q: Blue-Green กับ Canary อันไหนดี?

A: Blue-Green: ง่ายกว่า, switch 100% traffic ทีเดียว, rollback instant Canary: ค่อยๆ route traffic (1% → 10% → 50% → 100%), ลด blast radius ใช้ Blue-Green: simple apps, small team, ต้องการ fast rollback ใช้ Canary: large scale, ต้อง validate กับ real traffic ก่อน full deploy

Q: HA มีค่าใช้จ่ายเท่าไหร่?

A: Multi-AZ: เพิ่ม ~50-100% (double instances + cross-AZ traffic) Multi-Region: เพิ่ม ~200-400% (full stack per region) ประหยัด: ใช้ spot instances สำหรับ non-critical, reserved instances สำหรับ baseline ROI: downtime 1 ชั่วโมง อาจเสียหาย $10K-$1M+ → HA คุ้มค่าสำหรับ business-critical

📖 บทความที่เกี่ยวข้อง

CircleCI Orbs Team Productivityอ่านบทความ → CircleCI Orbs Zero Downtime Deploymentอ่านบทความ → CircleCI Orbs Cloud Native Designอ่านบทความ → CircleCI Orbs Cost Optimization ลดค่าใช้จ่ายอ่านบทความ → CircleCI Orbs Container Orchestrationอ่านบทความ →

📚 ดูบทความทั้งหมด →