在赛博堡垒中,有时我们只想重装或卸载 ArgoCD 本身(比如迁移 GitOps 工具,或者清理测试环境),但绝不希望它把正在运行的业务应用(比如我们的存储大坝、可视化面板)一起删掉。
ArgoCD 在部署应用时,默认会给资源打上一个叫 resources-finalizer.argocd.argoproj.io 的终结器(相当于一根引爆线)。如果你直接执行 kubectl delete namespace argocd,它会顺着这根线把底层真实的 Pod 和 Service 全部“爆破”掉,甚至会导致整个命名空间卡死在 Terminating 状态。
要做到**“监工跑路,大楼照常营业”**,我们必须在拆除指挥中心前,偷偷剪断所有的引爆线。
为了绝对的安全,我们将采用**“暗杀级”**施工法:先切断监工的大脑,再从容拆除。
这是应对复杂 GitOps 架构最关键的一步。我们必须先把 ArgoCD 的应用控制器副本数缩容为 0,让其失去对集群状态的监听和自愈能力。
kubectl scale statefulset argocd-application-controller -n argocd --replicas=0
(💡 监理提示:执行后,ArgoCD 变成了“瞎子和聋子”,绝对不会再产生任何反扑动作。)
大脑死机后,我们就可以毫无顾忌地强制抹除所有 Application 对象的 Finalizer。
打开终端,执行这行“批量剪线”脚本:
kubectl get apps -n argocd -o name | xargs -I {} kubectl patch {} -n argocd -p '{"metadata": {"finalizers": null}}' --type merge
(💡 监理提示:执行完后,这些应用就已经彻底脱离 ArgoCD 的“同归于尽”机制了。)
既然引爆线已经没了,且没有控制器来阻挠,我们现在就可以安全地删掉 ArgoCD 里的那些“项目档案”了。
kubectl delete apps --all -n argocd
这条命令会瞬间执行完毕,而你集群里的真实业务应用完全不会受到任何影响,它们已经变成了 K8s 的原生脱管应用。
清空了档案后,我们就可以按图索骥,用当初浇筑时的官方图纸进行反向拆除,把 ArgoCD 的 Redis 缓存、API 服务等组件清理掉:
kubectl delete -n argocd -f https://raw.githubusercontent.com/argoproj/argo-cd/stable/manifests/install.yaml
最后一步,把划拨给 ArgoCD 的专属园区,以及它留在 K8s 底层的那些自定义资源定义(CRD)连根拔起。
1. 彻底粉碎专属 CRD:
(⚠️ 警告:这会删除全集群所有命名空间下的 ArgoCD 相关资源,确保你没有其他的 ArgoCD 实例在使用它们!)
kubectl delete crd applications.argoproj.io appprojects.argoproj.io applicationsets.argoproj.io
2. 抹平命名空间:
kubectl delete namespace argocd
在实际的集群拆迁中,K8s 的垃圾回收机制偶尔会发生死锁。如果你在执行上述步骤时卡住了,请使用以下“重火力”工程手段。
除了 Application,ArgoCD 的“项目对象” (AppProject) 也带有防删机制。如果你发现删除一直卡住,请再补上这一刀:
kubectl get appprojects -n argocd -o name | xargs -I {} kubectl patch {} -n argocd --type json -p='[{"op": "remove", "path": "/metadata/finalizers"}]' 2>/dev/null
ArgoCD 拥有控制整个集群的极高权限,这意味着它创建的某些 ClusterRole 是不受命名空间限制的。拆除后,我们可以用标签(Label)进行一次全局扫荡:
kubectl delete clusterrole -l app.kubernetes.io/part-of=argocd 2>/dev/null
kubectl delete clusterrolebinding -l app.kubernetes.io/part-of=argocd 2>/dev/null
如果所有的图纸都已经清理完毕,但最后执行 kubectl delete namespace argocd 时依然无限卡在 Terminating 状态。这意味着 K8s 底层的 API Server 陷入了死循环,通常是因为残留的无法解析的资源阻塞了垃圾回收。
请掏出这段极其危险但也极其有效的 API 强制注销指令(需要宿主机已安装 jq 工具):
kubectl get namespace argocd -o json | \
jq '.spec.finalizers = []' | \
kubectl replace --raw "/api/v1/namespaces/argocd/finalize" -f -
这条指令会直接绕过正常的垃圾回收流程,粗暴地把该园区的终结器全部清空,Namespace 瞬间就会灰飞烟灭!
至此,ArgoCD 已经被你彻底从集群中抹除,你可以使用 kubectl get pods -A 巡查一圈。
你会发现,argocd 命名空间已经彻底消失,且没有任何幽灵权限残留。但你之前通过它部署的真实业务,依然在各自的命名空间里稳健运行。现在,你可以随时重新安装一个崭新的 ArgoCD,再把它们重新“收编”回流水线中!