Argo CD + GitHub Actions สร้าง CI/CD Pipeline แบบ GitOps ครบวงจร

Argo CD + GitHub Actions: สร้าง CI/CD Pipeline แบบ GitOps ครบวงจร

บทนำ: GitOps คืออะไร

GitOps เป็นแนวทางการจัดการ Infrastructure ที่ใช้ Git repository เป็นแหล่งความจริง (Single Source of Truth) สำหรับทั้ง Application Code และ Infrastructure Configuration ด้วยวิธีนี้ ทำให้การ Deploy มีความปลอดภัย ติดตามได้ และสามารถ Rollback ได้ง่าย

บทความนี้จะอธิบายการสร้าง CI/CD Pipeline แบบ GitOps ที่ผสมผสาน GitHub Actions (สำหรับ Continuous Integration) กับ Argo CD (สำหรับ Continuous Deployment) ให้ทำงานสอดประสานกันเป็นระบบสมบูรณ์

สถาปัตยกรรมของ GitOps Pipeline

ระบบ CI/CD Pipeline แบบ GitOps มีขั้นตอนหลักดังนี้:

  1. Code Push: Developer push code ไปยัง GitHub
  2. GitHub Actions (CI): Trigger workflow อัตโนมัติ build Docker image และ push ไปยัง Docker Registry
  3. Update Manifest: GitHub Actions อัพเดตไฟล์ Kubernetes manifest (deployment.yaml) ในอีก repository เพื่อระบุ image tag ใหม่
  4. Argo CD (CD): ตรวจสอบการเปลี่ยนแปลงใน Git repository และ auto-sync manifest ไปยัง Kubernetes cluster
  5. Deploy: Application ถูก deploy ไปยัง Kubernetes cluster โดยอัตโนมัติ

ข้อดีของสถาปัตยกรรมนี้คือ ทุกอย่างอยู่ใน Git – ติดตามประวัติได้ Audit trail ชัดเจน และสามารถ Rollback ได้ทันที

ตั้งค่า GitHub Actions Workflow

GitHub Actions ใช้ไฟล์ YAML ในโฟลเดอร์ .github/workflows/ เพื่อกำหนด Workflow Pipeline

ตัวอย่าง: ci-cd.yaml Workflow

name: CI/CD Pipeline with GitOps

on:
  push:
    branches:
      - main

env:
  REGISTRY: ghcr.io
  IMAGE_NAME: ${{ github.repository }}

jobs:
  build-and-push:
    runs-on: ubuntu-latest
    permissions:
      contents: read
      packages: write

    steps:
      - name: Checkout code
        uses: actions/checkout@v3

      - name: Set up Docker Buildx
        uses: docker/setup-buildx-action@v2

      - name: Login to Container Registry
        uses: docker/login-action@v2
        with:
          registry: ${{ env.REGISTRY }}
          username: ${{ github.actor }}
          password: ${{ secrets.GITHUB_TOKEN }}

      - name: Extract metadata
        id: meta
        uses: docker/metadata-action@v4
        with:
          images: ${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}
          tags: |
            type=ref,event=branch
            type=sha,prefix={{branch}}-
            type=semver,pattern={{version}}

      - name: Build and push Docker image
        uses: docker/build-push-action@v4
        with:
          context: .
          push: true
          tags: ${{ steps.meta.outputs.tags }}
          labels: ${{ steps.meta.outputs.labels }}

  update-manifests:
    needs: build-and-push
    runs-on: ubuntu-latest

    steps:
      - name: Checkout manifest repository
        uses: actions/checkout@v3
        with:
          repository: ${{ github.repository_owner }}/deployment-manifests
          token: ${{ secrets.GITHUB_TOKEN }}
          path: manifests

      - name: Update image tag in deployment manifest
        run: |
          cd manifests
          NEW_IMAGE="$REGISTRY/$IMAGE_NAME:${{ github.sha }}"
          sed -i "s|image: .*|image: $NEW_IMAGE|g" k8s/deployment.yaml

      - name: Commit and push changes
        run: |
          cd manifests
          git config --local user.email "[email protected]"
          git config --local user.name "GitHub Action"
          git add k8s/deployment.yaml
          git commit -m "Update image to ${{ github.sha }}" || echo "No changes"
          git push

ตั้งค่า Argo CD สำหรับ Deployment อัตโนมัติ

Argo CD ตรวจสอบ Git repository และ auto-sync manifest ไปยัง Kubernetes cluster โดยอัตโนมัติ

สร้าง Argo CD Application

apiVersion: argoproj.io/v1alpha1
kind: Application
metadata:
  name: my-app
  namespace: argocd
spec:
  project: default

  source:
    repoURL: https://github.com/your-org/deployment-manifests
    targetRevision: main
    path: k8s

  destination:
    server: https://kubernetes.default.svc
    namespace: production

  syncPolicy:
    automated:
      prune: true
      selfHeal: true
    syncOptions:
    - CreateNamespace=true

  revisionHistoryLimit: 10

ข้อมูลสำคัญ:

  • automated.prune: true – ลบ resource ที่ไม่มีอยู่ใน Git
  • automated.selfHeal: true – auto-sync เมื่อ cluster state เปลี่ยนแปลง
  • targetRevision: main – ใช้ branch main เป็นแหล่งความจริง

Kubernetes Manifest Structure

ไฟล์ deployment.yaml ที่จัดเก็บใน deployment-manifests repository:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: my-app
  namespace: production
spec:
  replicas: 3
  selector:
    matchLabels:
      app: my-app
  template:
    metadata:
      labels:
        app: my-app
    spec:
      containers:
      - name: app
        image: ghcr.io/your-org/repo-name:abc123def456
        ports:
        - containerPort: 8080
        resources:
          requests:
            memory: "256Mi"
            cpu: "250m"
          limits:
            memory: "512Mi"
            cpu: "500m"
---
apiVersion: v1
kind: Service
metadata:
  name: my-app-service
  namespace: production
spec:
  type: ClusterIP
  selector:
    app: my-app
  ports:
  - protocol: TCP
    port: 80
    targetPort: 8080

ความต้องการของ Infrastructure

สำหรับ GitOps Pipeline แบบเต็มรูปแบบ คุณจำเป็นต้องมี:

  • Kubernetes Cluster: สำหรับ Argo CD และ Application Deployment
  • Container Registry: Docker Registry หรือ GitHub Container Registry
  • Git Repositories: สองอย่าง – Application Code และ Deployment Manifests
  • CI/CD Runner: GitHub Actions (built-in) หรือ Self-hosted Runner

บริการ ผู้ให้บริการโฮสติ้ง Cloud VPS (https://de.co.th/cloud-vps) เหมาะสมสำหรับการ Host Kubernetes Cluster ที่มีประสิทธิภาพสูง ความปลอดภัยเชื่อถือได้ และ Support ที่เป็นมืออาชีพ

ขั้นตอนการตั้งค่าแบบ Step-by-Step

ขั้นที่ 1: เตรียม GitHub Repositories

  1. สร้าง repository สำหรับ Application Code (ที่มีไฟล์ Dockerfile)
  2. สร้าง repository สำหรับ Deployment Manifests (ที่มีไฟล์ YAML สำหรับ Kubernetes)
  3. ตั้งค่า GitHub Token พร้อมสิทธิ์ read/write

ขั้นที่ 2: ตั้งค่า GitHub Actions

  1. สร้างโฟลเดอร์ .github/workflows/ ใน repository ของ Application Code
  2. สร้างไฟล์ ci-cd.yaml ตามตัวอย่างข้างต้น
  3. ตั้งค่า Secrets ใน GitHub (Settings > Secrets and variables > Actions)

ขั้นที่ 3: ติดตั้ง Argo CD

  1. ติดตั้ง Argo CD บน Kubernetes: kubectl create namespace argocd && kubectl apply -n argocd -f https://raw.githubusercontent.com/argoproj/argo-cd/stable/manifests/install.yaml
  2. Expose Argo CD Server: kubectl port-forward svc/argocd-server -n argocd 8080:443
  3. ล็อกอินและสร้าง Application ตามตัวอย่างข้างต้น

ขั้นที่ 4: ทดสอบ Pipeline

  1. Push code ใหม่ไปยัง main branch
  2. ตรวจสอบ GitHub Actions workflow ว่า build และ push สำเร็จ
  3. ตรวจสอบ Argo CD ว่า sync manifest และ deploy application สำเร็จ

Best Practices สำหรับ GitOps

  • Separate Repositories: แยก Application Code และ Infrastructure Config
  • Version Control All: ทุกอย่างอยู่ใน Git เพื่อให้สามารถติดตามประวัติ
  • Signed Commits: ใช้ GPG signing เพื่อความปลอดภัย
  • Pull Request Reviews: ต้องผ่าน Code Review ก่อน Merge
  • Policy as Code: ใช้ tools เช่น OPA/Gatekeeper สำหรับการควบคุม
  • Secrets Management: ใช้ Sealed Secrets หรือ External Secrets Operator
  • Monitoring and Logging: ติดตั้ง Prometheus และ Grafana สำหรับ Visibility

การแก้ไขปัญหาทั่วไป

Argo CD ไม่ Sync โดยอัตโนมัติ: ตรวจสอบ SSH key หรือ HTTPS credentials สำหรับ Git repository และ Argo CD logs: kubectl logs -n argocd deployment/argocd-application-controller

GitHub Actions ล้มเหลว: ตรวจสอบ logs ใน GitHub Actions tab และยืนยัน Secrets ตั้งค่าถูกต้อง

Image ใหม่ไม่ Deploy: ตรวจสอบว่า GitHub Actions ได้ push tag ใหม่และ Argo CD ได้รับการแจ้งเตือน

สรุป

การสร้าง CI/CD Pipeline แบบ GitOps ด้วย Argo CD และ GitHub Actions นำเสนอวิธีที่ปลอดภัย ติดตามได้ และยืดหยุ่นสำหรับการ Deploy Application ขนาดใหญ่ โดยใช้ Git เป็นแหล่งความจริง ทำให้การจัดการ Infrastructure มีความโปร่งใสและเหมาะสำหรับการทำงานร่วมกัน

หากต้องการ Infrastructure ที่สมบูรณ์สำหรับ DevOps Pipeline นี้ ผู้ให้บริการโฮสติ้ง Cloud VPS มอบการสนับสนุนและความน่าเชื่อถือสูงสุดเพื่อให้ Pipeline ของคุณทำงานได้อย่างราบรื่น