Pod 亲和性(podAffinity)主要解决 Pod 可以和哪些 Pod 部署在同一个拓扑域中的问题(其中拓扑域用主机标签实现,可以是单个主机,也可以是多个主机组成的 cluster、zone 等等),而 Pod 反亲和性主要是解决 Pod 不能和哪些 Pod 部署在同一个拓扑域中的问题,它们都是处理的 Pod 与 Pod 之间的关系,比如一个 Pod 在一个节点上了,那么我这个也得在这个节点,或者你这个 Pod 在节点上了,那么我就不想和你待在同一个节点上。
由于我们这里只有一个集群,并没有区域或者机房的概念,所以我们这里直接使用主机名来作为拓扑域,把 Pod 创建在同一个主机上面。
1 2 3 4 5 6 7
$ kubectl get nodes --show-labels NAME STATUS ROLES AGE VERSION LABELS ydzs-master Ready master 55d v1.16.2 beta.kubernetes.io/arch=amd64,beta.kubernetes.io/os=linux,kubernetes.io/arch=amd64,kubernetes.io/hostname=ydzs-master,kubernetes.io/os=linux,node-role.kubernetes.io/master= ydzs-node1 Ready <none> 55d v1.16.2 beta.kubernetes.io/arch=amd64,beta.kubernetes.io/fluentd-ds-ready=true,beta.kubernetes.io/os=linux,kubernetes.io/arch=amd64,kubernetes.io/hostname=ydzs-node1,kubernetes.io/os=linux ydzs-node2 Ready <none> 55d v1.16.2 beta.kubernetes.io/arch=amd64,beta.kubernetes.io/fluentd-ds-ready=true,beta.kubernetes.io/os=linux,com=youdianzhishi,kubernetes.io/arch=amd64,kubernetes.io/hostname=ydzs-node2,kubernetes.io/os=linux ydzs-node3 Ready <none> 53d v1.16.2 beta.kubernetes.io/arch=amd64,beta.kubernetes.io/fluentd-ds-ready=true,beta.kubernetes.io/os=linux,kubernetes.io/arch=amd64,kubernetes.io/hostname=ydzs-node3,kubernetes.io/os=linux,monitor=prometheus ydzs-node4 Ready <none> 53d v1.16.2 beta.kubernetes.io/arch=amd64,beta.kubernetes.io/fluentd-ds-ready=true,beta.kubernetes.io/os=linux,kubernetes.io/arch=amd64,kubernetes.io/hostname=ydzs-node4,kubernetes.io/os=linux
同样,还是针对上面的资源对象,我们来测试下 Pod 的亲和性:(pod-affinity-demo.yaml)
$ kubectl delete -f node-selector-demo.yaml pod "test-busybox" deleted $ kubectl delete -f pod-affinity-demo.yaml deployment.apps "pod-affinity" deleted $ kubectl apply -f pod-affinity-demo.yaml deployment.apps/pod-affinity created $ kubectl get pods -o wide -l app=pod-affinity NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES pod-affinity-587f9b5b58-bbfgr 0/1 Pending 0 18s <none> <none> <none> <none> pod-affinity-587f9b5b58-lwc8n 0/1 Pending 0 18s <none> <none> <none> <none> pod-affinity-587f9b5b58-pc7ql 0/1 Pending 0 18s <none> <none> <none> <none>
我们可以看到都处于 Pending 状态了,这是因为现在没有一个节点上面拥有 app=busybox-pod 这个标签的 Pod,而上面我们的调度使用的是硬策略,所以就没办法进行调度了,大家可以去尝试下重新将 test-busybox 这个 Pod 调度到其他节点上,观察下上面的3个副本会不会也被调度到对应的节点上去。
我们这个地方使用的是 kubernetes.io/hostname 这个拓扑域,意思就是我们当前调度的 Pod 要和目标的 Pod 处于同一个主机上面,因为要处于同一个拓扑域下面,为了说明这个问题,我们把拓扑域改成 beta.kubernetes.io/os,同样的我们当前调度的 Pod 要和目标的 Pod 处于同一个拓扑域中,目标的 Pod 是拥有 beta.kubernetes.io/os=linux 的标签,而我们这里所有节点都有这样的标签,这也就意味着我们所有节点都在同一个拓扑域中,所以我们这里的 Pod 可以被调度到任何一个节点,重新运行上面的 app=busybox-pod 的 Pod,然后再更新下我们这里的资源对象:
1 2 3 4 5
$ kubectl get pods -o wide -l app=pod-affinity NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES pod-affinity-76c56567c-792n4 1/1 Running 0 2m59s 10.244.2.254 ydzs-node2 <none> <none> pod-affinity-76c56567c-8s2pd 1/1 Running 0 3m53s 10.244.4.18 ydzs-node4 <none> <none> pod-affinity-76c56567c-hx7ck 1/1 Running 0 2m52s 10.244.3.23 ydzs-node3 <none> <none>