4. 污点与容忍入门:Taint 与 Toleration 概念、Effect 类型与基本语法
在 Kubernetes 集群中,调度器默认采用“资源匹配 + 亲和性”策略将 Pod 分配到合适的 Node。然而,实际生产环境往往需要更精细的“排斥”机制:某些 Node 应被预留(如 GPU 节点、专用计算节点),某些 Node 在故障或维护期间应禁止新 Pod 调度。Kubernetes 通过 Taint(污点) 与 Toleration(容忍) 实现了这一能力——Node 打上污点以“排斥”不匹配的 Pod,Pod 声明容忍以“突破”排斥。
4.1 核心概念
- Taint(污点):附加在 Node 上的键值对属性,包含一个
Effect字段,用于定义对 Pod 的排斥行为。Node 可以拥有多个污点。 - Toleration(容忍):附加在 Pod 上的声明,表示该 Pod 能够“容忍”某个或某些污点。容忍不保证调度到该 Node,但允许调度器将 Pod 分配到带有对应污点的 Node。
- 调度决策逻辑:调度器检查 Node 的所有污点,如果 Pod 没有容忍其中任何一个污点,则根据 Effect 类型执行相应操作(禁止调度、尽量不调度或驱逐已有 Pod)。
关键理解: 污点是 Node 对 Pod 的“排斥条件”,容忍是 Pod 对排斥的“豁免声明”。两者共同构成 Kubernetes 中“白名单式”的调度控制模型。
4.2 Effect 类型详解
Kubernetes 定义了三种 Effect,决定了污点对 Pod 的影响程度:
| Effect 类型 | 行为描述 | 对未容忍 Pod 的影响 | 典型使用场景 |
|---|---|---|---|
NoSchedule |
强制禁止调度 | 调度器不会将未容忍该污点的 Pod 调度到该 Node | 专用节点(GPU、FPGA)、预留节点、故障节点 |
PreferNoSchedule |
尽量不调度(软约束) | 调度器会尽量避免,但如果没有其他可用 Node,仍可能调度 | 低优先级节点、临时维护节点、成本优化场景 |
NoExecute |
禁止调度 + 驱逐已有 Pod | 不仅禁止新 Pod 调度,还会驱逐 Node 上所有未容忍该污点的已有 Pod | 节点故障、安全隔离、节点下线、紧急维护 |
注意:
NoExecute 是最严厉的 Effect,它会立即影响正在运行的 Pod。生产环境中使用 NoExecute 时,务必确保关键 Pod 已配置对应的容忍,否则可能导致服务中断。
4.3 基本语法与操作
4.3.1 为 Node 添加污点
使用 kubectl taint 命令为 Node 添加污点,语法格式为:
kubectl taint nodes <node-name> <key>=<value>:<Effect>
示例:为 node-gpu-01 添加一个 GPU 专用污点:
kubectl taint nodes node-gpu-01 gpu=true:NoSchedule
该命令执行后,任何未声明 gpu=true 容忍的 Pod 都无法调度到 node-gpu-01。
4.3.2 在 Pod 中声明容忍
在 Pod 或 Deployment 的 spec.tolerations 字段中声明容忍,基本结构如下:
apiVersion: v1
kind: Pod
metadata:
name: gpu-pod
spec:
tolerations:
- key: "gpu"
operator: "Equal"
value: "true"
effect: "NoSchedule"
containers:
- name: gpu-container
image: nvidia/cuda:11.0-base
容忍字段说明:
key:污点的键,必须与 Node 污点的 key 匹配。operator:匹配运算符,支持Equal(精确匹配 key 和 value)和Exists(仅匹配 key,忽略 value)。value:当 operator 为Equal时,必须与污点的 value 一致。effect:可选字段,指定容忍的 Effect 类型。如果省略,则容忍所有 Effect。tolerationSeconds:仅对NoExecute有效,指定 Pod 在被驱逐前可以继续运行的秒数。
4.3.3 查看与删除污点
查看 Node 污点:
kubectl describe node <node-name> | grep Taints
删除污点(在末尾添加减号):
kubectl taint nodes <node-name> <key>=<value>:<Effect>-
示例:删除 node-gpu-01 上的 GPU 污点:
kubectl taint nodes node-gpu-01 gpu=true:NoSchedule-
4.4 污点与容忍工作流程
4.5 常见操作模式
模式一:专用节点隔离
为 GPU 节点添加
为 GPU 节点添加
gpu=true:NoSchedule,仅允许声明了对应容忍的 AI 训练 Pod 调度。
模式二:节点维护
在节点维护前添加
在节点维护前添加
maintenance=true:NoExecute,自动驱逐未容忍的 Pod,同时阻止新 Pod 调度。
模式三:软约束成本优化
为低成本竞价实例节点添加
为低成本竞价实例节点添加
spot=true:PreferNoSchedule,优先使用普通节点,但在资源紧张时允许调度。
4.6 避坑指南
- 容忍不匹配:容忍的
key、value、effect必须与污点完全匹配(或使用Exists运算符),否则容忍无效。 - 多个污点叠加:Node 可以同时拥有多个污点,Pod 必须容忍所有污点才能被调度。只要有一个污点未容忍,调度器就会根据 Effect 拒绝调度。
- NoExecute 的驱逐延迟:通过
tolerationSeconds可以为 Pod 设置驱逐宽限期,适用于需要优雅退出的工作负载。 - 容忍不等于亲和:容忍只解除排斥,不保证 Pod 一定会调度到该 Node。如果需要强制调度,需结合
nodeSelector或节点亲和性。
4.7 本章小结
污点与容忍是 Kubernetes 调度体系中实现“节点隔离”与“调度控制”的核心机制。通过三种 Effect 类型(NoSchedule、PreferNoSchedule、NoExecute),运维人员可以精确控制 Pod 与 Node 之间的调度关系。掌握污点与容忍的基本语法和匹配规则,是后续学习高级调度策略(如节点亲和性、Pod 拓扑分布约束)的基础。