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 可能产生以下冲突:
- 手动扩缩容被覆盖:运维人员临时增加 Pod 副本数应对流量高峰,Self-Heal 会立即将其还原为 Git 中的副本数。
- 滚动升级进度被中断:如果滚动升级过程中出现短暂的
CrashLoopBackOff,Self-Heal 可能判定为“偏离期望状态”,触发回滚或重新同步。 - 资源配额争抢: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 同步策略与滚动升级的交互流程
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 滚动升级期间的手动操作流程
- 暂停自动同步:
argocd app set <APP> --sync-policy automated='{"prune":false,"selfHeal":false}' - 执行滚动升级:通过
kubectl set image或修改 Git 仓库中的镜像版本 - 监控升级状态:使用
kubectl rollout status deployment/<NAME>确认 Pod 健康 - 手动同步:
argocd app sync <APP> --prune=false - 验证通过后恢复策略:重新启用自动同步和 Self-Heal
避坑提醒:不要在滚动升级过程中同时修改 Git 仓库中的多个资源(如 ConfigMap + Deployment),Argo CD 的自动同步可能以非预期顺序应用变更,导致 Pod 配置不一致。建议先更新 ConfigMap,手动同步确认无误后再更新 Deployment。