拓扑域由节点标签定义
拓扑类约束(Pod 亲和与反亲和、拓扑分布约束、卷拓扑)都用 topologyKey 指定「域」:调度器按该标签的取值把节点分组,再要求副本落进不同分组或与目标 Pod 同组。kubernetes.io/hostname 是节点级域,topology.kubernetes.io/zone 与 region 分别对应可用区与地域。自建或裸金属集群如果没给节点打 zone 标签,跨可用区分散、卷亲和、就近路由都会失准,所以标签体系是拓扑策略的前置条件。
基本信息
| 适用平台 | Kubernetes 各版本,调度与存储共用同一套节点标签 |
|---|---|
| 使用位置 | affinity.topologyKey、topologySpreadConstraints.topologyKey、卷的节点亲和 |
| 标准标签 | kubernetes.io/hostname、topology.kubernetes.io/zone、topology.kubernetes.io/region |
| 查看方式 | kubectl get nodes -L 标签键,逐个核对覆盖情况 |
| 前置条件 | 拓扑域标签必须在参与调度的节点上都存在 |
典型使用场景
- 高可用部署:要求同一应用的副本分散到不同可用区
- 成本与就近:把访问密集的组件放在同一可用区减少跨区流量
- 单节点唯一:用 hostname 域让每节点只跑一个副本(如日志采集)
- 存储协同:让 Pod 与数据所在可用区一致,避免跨区挂载
- 混合规格集群:按实例规格分组,把任务放到合适机型
拓扑分布约束示例
拓扑分布约束示例
spec:
topologySpreadConstraints:
- maxSkew: 1 # 各域之间副本数最大差值
topologyKey: topology.kubernetes.io/zone
whenUnsatisfiable: ScheduleAnyway # 也可用 DoNotSchedule 卡住
labelSelector:
matchLabels:
app: web核对标签覆盖
核对标签覆盖
kubectl get nodes -L topology.kubernetes.io/zone -L topology.kubernetes.io/region
kubectl get nodes -L kubernetes.io/hostname -L node.kubernetes.io/instance-type
kubectl get pod web-x -o wide # 对照实际落点与节点分布
kubectl describe pod web-x | grep -i -A3 'topology\|affinity'常用拓扑域标签
| 标签键 | 含义 | 常见用途 |
|---|---|---|
| kubernetes.io/hostname | 节点名(节点级域) | Pod 反亲和、每节点一个副本 |
| topology.kubernetes.io/zone | 可用区 | 跨区分散、卷拓扑 |
| topology.kubernetes.io/region | 地域 | 多地域部署与就近访问 |
| node.kubernetes.io/instance-type | 实例规格 | 按机型分组调度 |
| 自定义标签(如机架) | 由运维自行定义 | 机架级容灾域 |
任何一个节点缺少该标签,都不会参与该拓扑域的判定:结果是约束悄悄失效、Pod 被集中到有标签的少数节点上,看事件也不一定有明显报错。
多云或混合集群的标签体系往往不统一,先统一命名(谁来打 zone、值怎么命名),再上拓扑策略,否则策略在不同集群上行为不一致。