1 背景

由于一些未知原因,一些namespace在删除时会一直处于Terminating状态,无法彻底删除

[root@master ~]# kubectl get ns crt-test
NAME       STATUS        AGE
crt-test   Terminating   71d

2 处理方式

2.1 删除对应资源的finalizers字段

finalizers字段属于K8S的GC垃圾收集器,是一种删除拦截机制,能够让控制器实现异步的删除前回调,从而在删除目标资源前清理相关资源或基础设施。当资源被删除时,API server将为该对象设置metadata.deletionTimestamp,然后控制器会试图满足资源的finalizers条件。 每当一个finalizer条件被满足时,控制器就会从资源的finalizers字段中删除该键。 直到finalizers字段为空时,对象才会被自动删除。

由于某些异常原因,finalizers条件无法满足,该资源就会一直处于Terminating状态,这个时候我们就可以手动edit这个资源,删除对应的finalizer条件,

kubectl edit ns crt-test

2.2 强制删除

在实际操作时,有时候edit资源删除finalizer无法生效,这时候可以试试调用api直接删除etcd里的数据,但是这种方式会出现无主资源,也就是尽管namespace本身被删除,但是底下的资源依然存在,

NAMESPACE=your-namespace
kubectl proxy &
kubectl get namespace $NAMESPACE -o json |jq '.spec = {"finalizers":[]}' >temp.json
curl -k -H "Content-Type: application/json" -X PUT --data-binary @temp.json 127.0.0.1:8001/api/v1/namespaces/$NAMESPACE/finalize

实际也是去删除finalize,但是采用更直接的方式,

2.3 删除namespace下所有资源

有时候如果namespace里还有其他资源,那么该namespace也是无法被删除的,那我们就可以通过手动删除该namespace下的资源。

kubectl delete all --all -n crt-test

但是该方式只会删除部分资源,这里all对应的并不是所有资源,只包含了pod,service,daemonset,deployment,replicaset,statefulset,job,cronjobs,因此对于一些CRD是无法删除的。

这时候我们可以使用kubectl api-resources来查看该集群下的所有资源,然后在该namespace下查一遍,

kubectl api-resources --verbs=list --namespaced -o name   | xargs -n 1 kubectl get --show-kind --ignore-not-found -n crt-test

能查,自然能删,

kubectl api-resources --verbs=delete --namespaced -o name   | xargs -n 1 kubectl delete --all -n crt-test

当然,删除资源的时候也有可能会卡主,可以继续尝试上面提到的删除finalizer方式。


参考文档:

  1. https://kubernetes.io/docs/concepts/overview/working-with-objects/finalizers/
  2. https://www.studytonight.com/post/how-to-list-all-resources-in-a-kubernetes-namespace
  3. https://stackoverflow.com/questions/52369247/namespace-stuck-as-terminating-how-i-removed-it
Logo

K8S/Kubernetes社区为您提供最前沿的新闻资讯和知识内容

更多推荐