DEBUG.WIKI
京东云;让 AI 进入真实业务;零售 · 物流 · 客服 · 硬件;查看方案 →
ZgoCloud:多地区部署,按需选节点;日本、美国、香港、德国
Evoxt;最高 6.0GHz CPU;高频云服务器 · 免费每周备份;查看配置 →

单节点 Kubernetes Pod 一直 Pending:控制平面污点未被容忍

单节点 Kubernetes Pod Pending 且事件明确指出控制平面污点时,先核对隔离策略,再选择 worker 或限定的 toleration,保留变更与恢复影响。

单节点 Kubernetes 集群中,几个不同应用的 Pod 都停在 Pending、READY 0/1,describe 显示 FailedScheduling,原因包含 untolerated taint 或 had taint ... that the pod didn't tolerate。节点的控制平面污点没有对应 toleration 时,Pod 尚未被分配到节点,容器还没有开始运行。

本文针对调度事件明确指向 node-role.kubernetes.io/control-plane 或旧名称 node-role.kubernetes.io/master 的情况。Ready 节点仍可以拒绝普通工作负载;但并非所有 Pending 都由污点造成,卷绑定、资源不足和亲和性也会阻止调度。

看 PodScheduled 与节点污点

以下对象名称是示例,需替换为实际命名空间、Pod 和节点:

kubectl describe pod example-app-abc123 -n team-app
kubectl get nodes
kubectl describe node control-01

Pod 的 Node 若是 <none>,PodScheduled 为 False,且最新事件指出控制平面 taint,才继续核对这一条件。旧事件可能仍保留,应结合当前状态和最新时间判断。

节点详细信息里的 Taints 会给出 key、value 和 effect。kubeadm 创建的控制平面通常带 node-role.kubernetes.io/control-plane:NoSchedule;旧集群可能用 master 名称,其他安装方式也可能采用不同策略。使用节点实际值,不要仅按教程版本猜 key。

NoSchedule 阻止没有匹配容忍的新 Pod 调度到该节点,本身不会驱逐已经运行的 Pod。NoExecute 的效果不同,既可能影响调度,也可能驱逐未被容忍的运行中 Pod,不能只保留 key 而忽略 effect。

保留控制平面隔离,还是允许特定应用运行

如果集群需要隔离控制平面,应增加或恢复可承载业务的 worker 节点,检查它们是否 Ready、是否有足够资源,以及是否符合应用的调度约束。给控制平面加 toleration 不能替代这一部署要求。

在自己管理的单机实验集群,已经决定允许某个工作负载共享控制平面时,可以只给该工作负载增加匹配的 toleration。应用会与 API server 等组件竞争 CPU、内存和磁盘,先确认资源预算及失效影响,不把实验配置直接用于需要隔离的生产集群。

下面是 Deployment 模板的局部示例,保留原有容器、标签和其他字段:

spec:
  template:
    spec:
      tolerations:
        - key: "node-role.kubernetes.io/control-plane"
          operator: "Exists"
          effect: "NoSchedule"

只有实际节点使用该 key 和 effect 时才适用。若节点是旧 master 污点,应使用对应的旧 key;不要为了保险添加空 key 的 Exists,让 Pod 无条件容忍所有污点。

Deployment 要修改 spec.template.spec,让新 Pod 从控制器模板取得设置;裸 Pod 的配置层级是 spec.tolerations。保存原工作负载清单,再按现有部署流程发布,模板更新会触发新 Pod 的滚动替换,应检查副本数、维护安排和应用就绪状态。只改由控制器生成的某个 Pod,不能可靠覆盖后续副本。

Toleration 只允许进入这类节点,不保证一定调度成功,也不强制选择控制平面。资源请求、节点亲和性及其他未匹配污点仍会参与判断;不要用 nodeName 强行绕过调度器来掩盖其他条件。

去除节点污点会扩大所有工作负载的可调度范围

若整个单机集群确实都允许在控制平面运行普通应用,可以由管理员按集群设计撤销指定节点上的指定污点。与模板 toleration 相比,这是节点级策略变更,其他没有 toleration 的 Pod 也可能随后被调度进来。

操作前保存节点的原污点 key、value、effect 以及工作负载安排,确保可以恢复。不要清空全部 taints,也不要把面向全部节点的去污点命令当成单个应用的修复。

恢复原 NoSchedule 污点可阻止后续不匹配 Pod 调度,但不会自动迁走已经运行的业务 Pod。若要重新隔离控制平面,还要安排工作负载迁移及服务可用性;不能通过改成 NoExecute 来突然驱逐它们。

验收要走到应用就绪

修改后查看实际新 Pod 的 tolerations、分配节点和最新事件。成功的第一步是 PodScheduled 变成 True,且不再出现同一个未容忍污点造成的调度拒绝。

随后确认镜像拉取、容器启动和应用自己的就绪检查都通过。Pod 获得节点后若进入 ImagePullBackOff 或挂载失败,属于下一阶段的故障;READY 0/1 不能单独区分这些原因。

需要撤回模板容忍时,按原清单恢复并观察新一轮替换。单节点上撤回后,新的业务 Pod 可能再次 Pending;应先准备 worker 或停用该实验工作负载,不能期待撤回权限后业务仍保持同样的运行位置。