跳到主要内容

GitOps与ArgoCD

1. 概念

GitOps = Git 是唯一事实来源。所有基础设施和应用配置存 Git,变更靠 PR。自动化工具监听 Git 变化,自动同步到集群。

Git 仓库(yaml / helm)
↓ watch
ArgoCD(或 Flux)
↓ sync
K8s 集群

核心原则:

  • 声明式(yaml 描述期望状态)
  • 版本化(git 历史 = 审计记录)
  • 自动同步(push 即生效)
  • 自愈(手动改集群会被 revert)

2. ArgoCD 安装

kubectl create namespace argocd
kubectl apply -n argocd -f https://raw.githubusercontent.com/argoproj/argo-cd/stable/manifests/install.yaml

# 获取 admin 初始密码
argocd admin initial-password -n argocd

# 暴露 UI
kubectl port-forward svc/argocd-server -n argocd 8080:443
# 访问 https://localhost:8080

CLI:

brew install argocd
argocd login localhost:8080 --username admin --password xxx --insecure

3. Application 定义

apiVersion: argoproj.io/v1alpha1
kind: Application
metadata:
name: my-frontend
namespace: argocd
spec:
project: default
source:
repoURL: https://github.com/myorg/k8s-configs.git
targetRevision: main
path: frontend/prod # yaml 所在目录
destination:
server: https://kubernetes.default.svc
namespace: frontend
syncPolicy:
automated:
prune: true # 删除 git 里没有的资源
selfHeal: true # 手动改了会恢复
syncOptions:
- CreateNamespace=true

4. 目录结构

k8s-configs/ # 独立 repo(配置和代码分离)
├── frontend/
│ ├── base/ # Kustomize base
│ │ ├── deployment.yaml
│ │ ├── service.yaml
│ │ ├── ingress.yaml
│ │ └── kustomization.yaml
│ ├── dev/
│ │ ├── kustomization.yaml # patch image tag / env
│ │ └── patches.yaml
│ ├── staging/
│ │ └── kustomization.yaml
│ └── prod/
│ └── kustomization.yaml
└── backend/
└── ...

或 Helm:

k8s-configs/
├── frontend/
│ ├── Chart.yaml
│ ├── values-dev.yaml
│ ├── values-staging.yaml
│ └── values-prod.yaml

5. CI 更新镜像 tag → 触发同步

# CI 里构建完镜像后更新 git repo
- name: Update image tag
run: |
cd k8s-configs
sed -i "s|image: myapp:.*|image: myapp:$}} github.sha }}|" frontend/prod/deployment.yaml
git add . && git commit -m "deploy frontend $}} github.sha }}" && git push

或用 ArgoCD Image Updater(自动监听 registry 新 tag):

metadata:
annotations:
argocd-image-updater.argoproj.io/image-list: web=ghcr.io/myorg/frontend
argocd-image-updater.argoproj.io/web.update-strategy: semver

6. 核心功能

6.1 Sync

  • OutOfSync:Git 和集群不一致
  • Synced:一致
  • Auto-Sync:自动对齐
argocd app sync my-frontend
argocd app diff my-frontend
argocd app get my-frontend

6.2 Rollback

argocd app history my-frontend
argocd app rollback my-frontend <revision>

或 revert git commit → ArgoCD 自动 sync 回去。

6.3 Wave / Hook

控制同步顺序:

metadata:
annotations:
argocd.argoproj.io/sync-wave: "1" # 0 先 1 后
argocd.argoproj.io/hook: PreSync # 同步前执行(如 migrate)

6.4 Health Check

ArgoCD 内置对 Deployment / Service / Ingress 的健康判断:

  • Healthy / Degraded / Progressing / Suspended / Missing

7. Multi-Cluster

argocd cluster add <context-name>

一套 ArgoCD 管多个集群(dev + staging + prod)。

8. SSO 集成

# argocd-cm ConfigMap
data:
dex.config: |
connectors:
- type: github
id: github
name: GitHub
config:
clientID: xxx
clientSecret: $dex.github.clientSecret
orgs:
- name: myorg

用 OIDC / GitHub / GitLab / LDAP 登录。

9. 与 Helm / Kustomize 集成

ArgoCD 原生支持:

  • 纯 yaml
  • Kustomize(path 下有 kustomization.yaml)
  • Helm chart(path 下有 Chart.yaml)
  • Jsonnet
  • 自定义 config management plugin

10. 最佳实践

实践说明
配置 repo 和代码 repo 分离配置变化不触发 CI build
PR review 配置变更不直接 push main
开 selfHeal防手动 kubectl edit 导致漂移
每环境一个 Applicationdev / staging / prod
用 App of Apps 模式一个 Application 管所有 Application
限制 ArgoCD 权限只能操作特定 namespace
Secret 用 sealed-secrets加密后提交 git

11. 常见反模式

  • CI 直接 kubectl apply:无审计、无 review
  • 配置和代码混一个 repo:每次代码改都触发 diff
  • 不开 selfHeal:人手动改了 git 不知道
  • prune 打开但没保护:git 误删 yaml = 生产资源被删
  • secret 明文存 git:即使私有 repo 也不安全
  • 不监控 OutOfSync:漂移了没人知
  • 一个 Application 管所有服务:一个挂全挂

12. 延伸阅读