官网链接:https://kubernetes.io/zh/docs/concepts/workloads/pods/pod-topology-spread-constraints/
Pod 拓扑分布约束
FEATURE STATE: Kubernetes v1.19 [stable]

你可以使用 拓扑分布约束(Topology Spread Constraints) 来控制 Pods 在集群内故障域 之间的分布,例如区域(Region)、可用区(Zone)、节点和其他用户自定义拓扑域。 这样做有助于实现高可用并提升资源利用率。
说明: 在 v1.18 之前的 Kubernetes 版本中,如果要使用 Pod 拓扑扩展约束,你必须在 API 服务器 和调度器 中启用 EvenPodsSpread 特性门控。

先决条件
节点标签

拓扑分布约束依赖于节点标签来标识每个节点所在的拓扑域。 例如,某节点可能具有标签:node=node1,zone=us-east-1a,region=us-east-1

假设你拥有具有以下标签的一个 4 节点集群:

NAME STATUS ROLES AGE VERSION LABELS
node1 Ready 4m26s v1.16.0 node=node1,zone=zoneA
node2 Ready 3m58s v1.16.0 node=node2,zone=zoneA
node3 Ready 3m17s v1.16.0 node=node3,zone=zoneB
node4 Ready 2m43s v1.16.0 node=node4,zone=zoneB

然后从逻辑上看集群如下:
在这里插入图片描述

你可以复用在大多数集群上自动创建和填充的 常用标签, 而不是手动添加标签。
Pod 的分布约束
API

pod.spec.topologySpreadConstraints 字段定义如下所示:

apiVersion: v1
kind: Pod
metadata:
  name: mypod
spec:
  topologySpreadConstraints:
    - maxSkew: <integer>
      topologyKey: <string>
      whenUnsatisfiable: <string>
      labelSelector: <object>

你可以定义一个或多个 topologySpreadConstraint 来指示 kube-scheduler 如何根据与现有的 Pod 的关联关系将每个传入的 Pod 部署到集群中。字段包括:

maxSkew 描述 Pod 分布不均的程度。这是给定拓扑类型中任意两个拓扑域中 匹配的 pod 之间的最大允许差值。它必须大于零。取决于 whenUnsatisfiable 的 取值,其语义会有不同。
    当 whenUnsatisfiable 等于 "DoNotSchedule" 时,maxSkew 是目标拓扑域 中匹配的 Pod 数与全局最小值之间可存在的差异。
    当 whenUnsatisfiable 等于 "ScheduleAnyway" 时,调度器会更为偏向能够降低 偏差值的拓扑域。
topologyKey 是节点标签的键。如果两个节点使用此键标记并且具有相同的标签值, 则调度器会将这两个节点视为处于同一拓扑域中。调度器试图在每个拓扑域中放置数量 均衡的 Pod。
whenUnsatisfiable 指示如果 Pod 不满足分布约束时如何处理:
    DoNotSchedule(默认)告诉调度器不要调度。
    ScheduleAnyway 告诉调度器仍然继续调度,只是根据如何能将偏差最小化来对 节点进行排序。
labelSelector 用于查找匹配的 pod。匹配此标签的 Pod 将被统计,以确定相应 拓扑域中 Pod 的数量。 有关详细信息,请参考标签选择算符。

测试 zong可用均匀分布 dep (单独使用topo资源貌似不太行 加上了反亲和 podAntiAffinity 测试可用)

apiVersion: apps/v1
kind: Deployment
metadata:
  creationTimestamp: null
  labels:
    app: topo-dep
  name: topo-dep
spec:
  replicas: 10
  selector:
    matchLabels:
      app: topo-dep
  strategy: {}
  template:
    metadata:
      creationTimestamp: null
      labels:
        app: topo-dep
    spec:
      affinity:
        podAntiAffinity:
          requiredDuringSchedulingIgnoredDuringExecution:
            - labelSelector:
                matchExpressions:
                  - key: app
                    operator: In
                    values:
                      - topo-dep
              topologyKey: kubernetes.io/hostname
      topologySpreadConstraints:
      - maxSkew: 1
        topologyKey: zone
        whenUnsatisfiable: DoNotSchedule
        labelSelector:
          matchLabels:
            app: topo-dep
      containers:
      - image: nginx
        name: nginx
        resources: {}
status: {}

执行后结果,其中10.71.6.*是一个zone 10.71.26.*是另外一个 zone

kubectl get pod --show-labels -o wide
NAME                       READY   STATUS              RESTARTS   AGE   IP              NODE          NOMINATED NODE   READINESS GATES   LABELS
topo-dep-88996d69f-2j4nn   1/1     Running             0          10s   172.16.0.130    10.71.6.13    <none>           <none>            app=topo-dep,pod-template-hash=88996d69f
topo-dep-88996d69f-2qrlk   1/1     Running             0          10s   172.16.12.89    10.71.26.3    <none>           <none>            app=topo-dep,pod-template-hash=88996d69f
topo-dep-88996d69f-4wd6b   1/1     Running             0          10s   172.16.4.38     10.71.26.10   <none>           <none>            app=topo-dep,pod-template-hash=88996d69f
topo-dep-88996d69f-6whnd   1/1     Running             0          10s   172.16.8.68     10.71.6.61    <none>           <none>            app=topo-dep,pod-template-hash=88996d69f
topo-dep-88996d69f-f4x2t   1/1     Running             0          10s   172.16.5.157    10.71.6.26    <none>           <none>            app=topo-dep,pod-template-hash=88996d69f
topo-dep-88996d69f-h5jww   0/1     ContainerCreating   0          10s   <none>          10.71.6.15    <none>           <none>            app=topo-dep,pod-template-hash=88996d69f
topo-dep-88996d69f-j2wbq   1/1     Running             0          10s   172.16.0.27     10.71.6.17    <none>           <none>            app=topo-dep,pod-template-hash=88996d69f
topo-dep-88996d69f-nlml6   1/1     Running             0          10s   172.16.7.114    10.71.6.62    <none>           <none>            app=topo-dep,pod-template-hash=88996d69f
topo-dep-88996d69f-tfv98   1/1     Running             0          10s   172.16.9.54     10.71.26.5    <none>           <none>            app=topo-dep,pod-template-hash=88996d69f
topo-dep-88996d69f-w66j8   1/1     Running             0          10s   172.16.11.111   10.71.26.16   <none>           <none>            app=topo-dep,pod-template-hash=88996d69f

另外一种方法推荐阅读:https://blog.51cto.com/tuwei/3683132

Logo

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

更多推荐