3. Node 故障域:节点级故障对 Pod 的影响与排错机制
节点是 Kubernetes 集群中最基本的计算单元。当节点发生硬件故障、内核崩溃或 kubelet 失联时,运行在该节点上的所有 Pod 都会受到影响。理解 Node Condition 与 Taint/Toleration 机制,是快速定位节点级故障、保障工作负载高可用的核心能力。
3.1 节点级故障类型与影响范围
节点级故障按来源可分为三类:硬件故障、内核故障、kubelet 故障。不同故障对 Pod 的影响程度和恢复路径差异显著。
| 故障类型 | 典型场景 | 对 Pod 的影响 | 恢复方式 |
|---|---|---|---|
| 硬件故障 | 磁盘损坏、内存 ECC 错误、网卡失效、电源异常 | Pod 运行异常或直接终止;数据持久化可能失败 | 节点修复或替换;Pod 由控制器重新调度 |
| 内核故障 | 内核 Panic、OOM Killer 误杀、文件系统死锁 | 节点完全不可用;Pod 状态变为 Unknown | 节点重启或重建;Pod 等待 eviction 超时 |
| kubelet 故障 | kubelet 进程崩溃、证书过期、与 API Server 断连 | Pod 状态无法更新;新 Pod 无法调度到该节点 | 修复 kubelet 或重启服务;节点自动恢复 |
排错经验: 硬件故障通常伴随节点指标异常(如磁盘 I/O 超时、内存错误计数增长),而 kubelet 故障时节点可能仍在运行,但 API Server 已无法感知其状态。优先检查
kubectl describe node 中的 Condition 字段。
3.2 Node Condition 机制
Node Condition 是节点状态的核心表达方式。kubelet 定期上报节点健康状况,API Server 将其记录在 .status.conditions 中。每个 Condition 包含 type、status、lastHeartbeatTime、lastTransitionTime、reason 和 message 六个字段。
核心 Condition 类型
| Condition 类型 | 含义 | 典型故障值 |
|---|---|---|
Ready |
节点是否可接受新 Pod | Unknown(kubelet 失联)或 False(磁盘压力等) |
DiskPressure |
节点磁盘空间不足 | True 时触发 Pod eviction |
MemoryPressure |
节点内存资源紧张 | True 时触发 QoS 降级 |
PIDPressure |
节点 PID 数量接近上限 | True 时新进程创建失败 |
NetworkUnavailable |
节点网络配置异常 | True 时 Pod 网络不通 |
排错命令:
# 查看节点所有 Condition
kubectl get node <node-name> -o jsonpath='{.status.conditions[*].type}'
# 查看 Ready Condition 的详细原因
kubectl describe node <node-name> | grep -A 5 "Conditions:"
3.3 Taint/Toleration 机制
当节点出现故障时,Kubernetes 通过 Taint 机制阻止新 Pod 调度到该节点,并驱逐已有 Pod。Taint 由 key、value、effect 三要素组成。Pod 必须设置匹配的 Toleration 才能容忍该 Taint。
三种 Effect 及其行为
| Effect | 行为 | 典型用途 |
|---|---|---|
NoSchedule |
新 Pod 不会调度到该节点(已有 Pod 不受影响) | 节点维护前标记 |
PreferNoSchedule |
尽量不调度,但不强制 | 资源紧张时软约束 |
NoExecute |
新 Pod 不调度 + 已有 Pod 被驱逐 | 节点故障时自动驱逐 |
节点故障自动 Taint
当 Node Condition 异常时,kube-controller-manager 中的 node-lifecycle-controller 会自动为节点添加 Taint:
| Condition 异常 | 自动添加的 Taint | Effect |
|---|---|---|
Ready == Unknown 超过 1 分钟 |
node.kubernetes.io/unreachable |
NoExecute |
Ready == False 超过 1 分钟 |
node.kubernetes.io/not-ready |
NoExecute |
DiskPressure == True |
node.kubernetes.io/disk-pressure |
NoSchedule |
MemoryPressure == True |
node.kubernetes.io/memory-pressure |
NoSchedule |
PIDPressure == True |
node.kubernetes.io/pid-pressure |
NoSchedule |
| 网络不可用 | node.kubernetes.io/network-unavailable |
NoSchedule |
注意:
NoExecute 效果的 Taint 会触发 Pod 驱逐。默认情况下,Pod 如果没有对应的 Toleration,会在 tolerationSeconds 过期后被驱逐。对于关键系统组件(如 CoreDNS、kube-proxy),Kubernetes 会自动添加 Toleration,避免被误驱逐。
3.4 节点故障排错流程
当节点出现故障时,按以下步骤排查:
- 检查节点状态:
kubectl get nodes查看节点是否 Ready。 - 查看 Condition 详情:
kubectl describe node <node-name>定位异常 Condition。 - 检查 Taint:
kubectl describe node <node-name> | grep Taints确认自动添加的 Taint。 - 查看 Pod 状态:
kubectl get pods --all-namespaces --field-selector spec.nodeName=<node-name>确认受影响 Pod。 - 检查 kubelet 日志: SSH 到节点,查看
journalctl -u kubelet -n 100或/var/log/kubelet.log。 - 检查节点资源:
kubectl top node <node-name>查看 CPU/内存使用;SSH 后使用df -h、free -m、top确认硬件状态。
快速排错命令组合:
# 一键查看节点异常 Condition 和 Taint
kubectl describe node <node-name> | grep -E "(Conditions:|Taints:|Message:)"
# 查看节点上所有 Pod 的驱逐状态
kubectl get pods --all-namespaces --field-selector spec.nodeName=<node-name> -o wide | grep -E "Evicted|Unknown|Error"
3.5 节点故障域架构图
下图展示了节点故障从发生到影响 Pod 的完整链路,以及 Condition 与 Taint 的联动关系:
3.6 排错案例:节点 NotReady 导致 Pod 驱逐
场景: 某生产集群中,节点 node-03 因磁盘故障导致 kubelet 无法上报心跳,30 秒后节点状态变为 NotReady。
排错过程:
kubectl get nodes发现node-03状态为NotReady。kubectl describe node node-03显示ReadyCondition 为Unknown,reason为NodeStatusUnknown,message为Kubelet stopped posting node status。- 检查 Taint:节点自动添加了
node.kubernetes.io/unreachable:NoExecute。 - 查看 Pod:
kubectl get pods --field-selector spec.nodeName=node-03 -n production发现多个 Pod 处于Terminating状态。 - SSH 到节点:
journalctl -u kubelet -n 50发现大量failed to write to /var/lib/kubelet错误,确认磁盘故障。 - 修复磁盘后重启 kubelet,节点恢复
Ready,Taint 自动移除,新 Pod 重新调度。
关键参数:
--pod-eviction-timeout 控制节点不可达时 Pod 的驱逐等待时间,默认 5 分钟。对于关键业务,可设置 tolerationSeconds 延长容忍时间,避免短暂故障导致大规模驱逐。
3.7 节点故障域总结
| 机制 | 作用 | 排错关注点 |
|---|---|---|
| Node Condition | 反映节点健康状态 | 检查 Ready、DiskPressure、MemoryPressure 等 |
| Taint/Toleration | 控制 Pod 调度与驱逐 | 确认自动 Taint 类型和 Effect |
| kubelet 心跳 | 维持节点与 API Server 通信 | 检查 node-status-update-frequency 和 node-monitor-grace-period |
| Pod eviction | 故障节点上的 Pod 重新调度 | 关注 tolerationSeconds 和 pod-eviction-timeout |