4. Argo CD Sync 策略:自动同步与手动同步、Prune 策略、Self-Heal 机制对滚动升级的影响

在 Kubernetes 滚动升级过程中,Argo CD 的同步策略直接决定了集群实际状态与 Git 仓库期望状态之间的收敛速度、安全边界以及资源回收行为。错误配置同步策略可能导致滚动升级中断、旧版本 Pod 残留或无限回弹。本章从自动/手动同步、Prune 策略、Self-Heal 机制三个维度分析其对滚动升级的影响,并给出生产级配置建议。

4.1 自动同步 vs 手动同步

同步模式 触发方式 滚动升级场景适用性 风险等级
自动同步 Git 仓库变更后自动触发 低风险、快速迭代环境 中
手动同步 人工点击或 CLI 触发 生产环境、金丝雀发布 低
带策略的自动同步 自动 + 自愈 + Prune 组合 CI/CD 全自动化流水线 高

自动同步在滚动升级中的典型问题:当 Deployment 的 strategy.rollingUpdate.maxSurge 或 maxUnavailable 与资源配额冲突时,自动同步会反复尝试更新,导致 Pod 频繁重建。手动同步则允许运维人员在配额校准后、确认集群压力正常时再执行同步,避免“同步风暴”。

生产建议:核心业务 Deployment 使用手动同步 + 审批流程;非关键 Job 或 CronJob 可使用自动同步,但必须配合 syncPolicy.syncOptions.Validate=false 避免校验阻塞。

4.2 Prune 策略:资源回收与滚动升级的冲突

Prune 策略控制 Argo CD 是否删除集群中不再存在于 Git 仓库中的资源。在滚动升级场景中,Prune 行为直接影响旧 ReplicaSet 的存留和回滚能力。

  • Prune=true:Argo CD 会在同步后立即删除所有未被 Git 管理的资源。滚动升级时,旧的 ReplicaSet 会被删除,导致无法快速回滚到上一版本。
  • Prune=false:旧资源保留,但集群中可能出现“孤儿资源”,增加 etcd 和 kube-apiserver 的负载。
  • Prune Propagation Policy:可设置为 foreground、background 或 orphan,影响级联删除行为。
滚动升级陷阱:当 prune=true 且 syncPolicy.syncOptions.PreserveResourcesOnDeletion=false 时,Argo CD 会在滚动升级完成后立即删除旧 ReplicaSet。如果新版本出现严重故障,你将无法通过 kubectl rollout undo 快速回滚,因为旧的 ReplicaSet 已被 Prune 清除。
# 推荐的生产级 Prune 配置:保留旧 ReplicaSet 24 小时
apiVersion: argoproj.io/v1alpha1
kind: Application
spec:
  syncPolicy:
    automated:
      prune: true
      selfHeal: true
    syncOptions:
      - PruneLast=true
      - PreserveResourcesOnDeletion=false
      - Replace=false

4.3 Self-Heal 机制:自动修复与滚动升级的博弈

Self-Heal 机制使 Argo CD 持续检测集群状态与 Git 期望状态的偏差,并自动纠正。在滚动升级过程中,Self-Heal 可能产生以下冲突:

  1. 手动扩缩容被覆盖:运维人员临时增加 Pod 副本数应对流量高峰,Self-Heal 会立即将其还原为 Git 中的副本数。
  2. 滚动升级进度被中断:如果滚动升级过程中出现短暂的 CrashLoopBackOff,Self-Heal 可能判定为“偏离期望状态”,触发回滚或重新同步。
  3. 资源配额争抢:Self-Heal 在检测到 Pod 数量不足时,会立即创建新 Pod,可能与正在终止的旧 Pod 争抢 CPU/内存配额。
最佳实践:在滚动升级期间临时关闭 Self-Heal,或使用 argocd app set <APP> --sync-policy automated='{"selfHeal":false}' 暂停自愈。升级完成并验证通过后,再重新启用。

4.4 三种策略对滚动升级的综合影响矩阵

策略组合 滚动升级速度 回滚能力 资源配额压力 运维复杂度
自动 + Prune + Self-Heal 快 低 高 低
手动 + Prune + Self-Heal 中 中 中 中
手动 + 无 Prune + 无 Self-Heal 慢 高 低 高
自动 + PruneLast + Self-Heal 快 中 中 低

4.5 同步策略与滚动升级的交互流程

同步策略与滚动升级交互流程 Git 仓库变更 同步策略判断 自动同步 / 手动同步 自动 手动 自动同步执行 等待人工确认 Prune 策略执行 Self-Heal 持续检测 ⚠ 滚动升级风险点 • 自动同步可能中断升级 • Prune 删除旧 ReplicaSet • Self-Heal 覆盖手动操作

4.6 生产环境推荐配置

针对滚动升级场景,推荐以下同步策略配置模板:

apiVersion: argoproj.io/v1alpha1
kind: Application
metadata:
  name: production-app
spec:
  syncPolicy:
    automated:
      prune: true
      selfHeal: false          # 滚动升级期间关闭自愈
    syncOptions:
      - PruneLast=true         # 最后执行 Prune,保留旧资源
      - RespectIgnoreDifferences=true
      - ApplyOutOfSyncOnly=true
    retry:
      limit: 3
      backoff:
        duration: 30s
        factor: 2
        maxDuration: 5m
关键参数说明:
PruneLast=true:确保新版本 Pod 全部就绪后再删除旧资源,保留回滚能力。
selfHeal=false:避免滚动升级过程中 Argo CD 与 Kubernetes 控制器产生冲突。
ApplyOutOfSyncOnly=true:只同步发生变更的资源,减少 API Server 压力。

4.7 滚动升级期间的手动操作流程

  1. 暂停自动同步:argocd app set <APP> --sync-policy automated='{"prune":false,"selfHeal":false}'
  2. 执行滚动升级:通过 kubectl set image 或修改 Git 仓库中的镜像版本
  3. 监控升级状态:使用 kubectl rollout status deployment/<NAME> 确认 Pod 健康
  4. 手动同步:argocd app sync <APP> --prune=false
  5. 验证通过后恢复策略:重新启用自动同步和 Self-Heal
避坑提醒:不要在滚动升级过程中同时修改 Git 仓库中的多个资源(如 ConfigMap + Deployment),Argo CD 的自动同步可能以非预期顺序应用变更,导致 Pod 配置不一致。建议先更新 ConfigMap,手动同步确认无误后再更新 Deployment。