K8S之Pod调度

Pod调度

在默认情况下,一个Pod在哪个Node节点上运行,是由Scheduler组件采用相关的算法计算得到的,这个过程不受人工控制的。但是在实际的使用过程中,这并不满足相关的需求,因为在很多的情况下,我们想控制某些Pod到达某些节点上,那么应该怎么做呢?这个就需要了解kubernetes对Pod的调度规则,kubernetes提供了四大类的调度方式:

  • 自动调度: 运行在哪个节点上完全由Secheduler经过一系列的算法计算得到的
  • 定向调度: NodeName、NodeSelector
  • 亲和性调度: NodeAffinity、PodAffinity、PodAntiAffinity
  • 污点(容忍)调度: Taints、Toleration

定向调度

定向调度,指的是利用在Pod上声明nodeName或者nodeSelector,以此将Pod调度到期望的node节点上。注意,这里的调度是强制的,这就意味着即使要调度的目标Node节点不存在,也会向上面进行调度,只不过pod运行失败而已。
NodeName

NodeName用于强制约束将Pod调度到指定的Name的Node节点上。这种方式,其实是直接跳过Scheduler的调度逻辑的,直接将Pod调度到指定名称的节点。

获取节点信息

创建一个pod-nodename.yaml文件

yaml 复制代码
apiVersion: v1
kind: Pod
metadata:
  name: pod-nodename
  namespace: dev
spec:
  containers:
  - name: nginx
    image: docker.1ms.run/library/nginx:latest
  nodeName: k8s-cluster-worker # 指定调度到 k8s-cluster-worker节点上

创建pod资源

查看pod的资源挂载情况

bash 复制代码
sudo kubectl get pod  pod-nodename -n dev  -o wide

改成不存在的节点上

重新创建pod资源

pod资源的状态 pod创建失败

bash 复制代码
sudo kubectl describe pod  pod-nodename -n dev  -o wide


NodeSelector

NodeSelector用于将pod调度到添加了指定标签的node节点上,他是通过kubernetes的label-selector机制 来实现的。也就是说,在pod创建之前,会由scheduler使用MatchNodeSelector调度策略进行label匹配,找出目标Node,然后将pod调度到目标节点,该匹配规则是强制约束

演示一下,需要先给node节点打标签

bash 复制代码
sudo kubectl label node k8s-cluster-worker nodeenv=pro

pod-nodeselector.yaml文件,并使用它创建Pod

yaml 复制代码
apiVersion: v1
kind: Pod
metadata:
  name: pod-nodeselector
  namespace: dev
spec:
  containers:
  - name: nginx
    image: docker.1ms.run/library/nginx:latest
  nodeSelector: 
    nodeenv: pro # 指定调度到具有nodeenv=pro标签的节点上

查看创建的pod资源挂载的节点

通过标签选择node节点成功

亲和性调度

上面的两种定向调度的方式,使用起来非常方便,但是也有一定的问题,那就是如果没有满足条件的Node,那么Pod将不会被运行,即使在集群中还有可用Node列表也不行,这就限制了它的使用场景。

基于上面的问题,kubernetes还提供了一种亲和性调度(Affinity) 。它在NodeSelector的基础之上的进行了扩展,可以通过配置的形式,实现优先选择满足条件的Node进行调度,如果没有,也可以调度到不满足条件的节点上,使调度更加灵活

Affinity主要分为三类:

  • nodeAffinity(node亲和性): 以node为目标,解决pod可以调度到哪些node的问题
  • podAffinity(pod亲和性) : 以pod为目标,解决pod可以和哪些已存在的pod部署在同一个拓扑域中的问题
  • podAntiAffinity(pod反亲和性) : 以pod为目标,解决pod不能和哪些已存在pod部署在同一个拓扑域中的问题

关于亲和性(反亲和性)使用场景的说明:
亲和性:如果两个应用频繁交互,那就有必要利用亲和性让两个应用的尽可能的靠近,这样可以减少因网络通信而带来的性能损耗。

反亲和性:当应用的采用多副本部署时,有必要采用反亲和性让各个应用实例打散分布在各个node上,这样可以提高服务的高可用性。

NodeAffinity

NodeAffinity的可配置项:

bash 复制代码
pod.spec.affinity.nodeAffinity
  requiredDuringSchedulingIgnoredDuringExecution  Node节点必须满足指定的所有规则才可以,相当于硬限制
    nodeSelectorTerms  节点选择列表
      matchFields   按节点字段列出的节点选择器要求列表
      matchExpressions   按节点标签列出的节点选择器要求列表(推荐)
        key    键
        values 值
        operat or 关系符 支持Exists, DoesNotExist, In, NotIn, Gt, Lt
  preferredDuringSchedulingIgnoredDuringExecution 优先调度到满足指定的规则的Node,相当于软限制 (倾向)
    preference   一个节点选择器项,与相应的权重相关联
      matchFields   按节点字段列出的节点选择器要求列表
      matchExpressions   按节点标签列出的节点选择器要求列表(推荐)
        key    键
        values 值
        operator 关系符 支持In, NotIn, Exists, DoesNotExist, Gt, Lt
	weight 倾向权重,在范围1-100。
bash 复制代码
关系符的使用说明:

- matchExpressions:
  - key: nodeenv              # 匹配存在标签的key为nodeenv的节点
    operator: Exists
  - key: nodeenv              # 匹配标签的key为nodeenv,且value是"xxx"或"yyy"的节点
    operator: In
    values: ["xxx","yyy"]
  - key: nodeenv              # 匹配标签的key为nodeenv,且value大于"xxx"的节点
    operator: Gt
    values: "xxx"

演示一下requiredDuringSchedulingIgnoredDuringExecution

创建pod-nodeaffinity-required.yaml

yaml 复制代码
apiVersion: v1
kind: Pod
metadata:
  name: pod-nodeaffinity-required
  namespace: dev
spec:
  containers:
  - name: nginx
    image: docker.1ms.run/library/nginx:latest
  affinity:  #亲和性设置
    nodeAffinity: #设置node亲和性
      requiredDuringSchedulingIgnoredDuringExecution: # 硬限制
        nodeSelectorTerms:
        - matchExpressions: # 匹配env的值在["xxx","yyy"]中的标签
          - key: nodeenv
            operator: In
            values: ["xxx","yyy"]

创建相关的pod资源

查看pod的资源信息

bash 复制代码
kubectl get pods pod-nodeaffinity-required -n dev -o wide
bash 复制代码
kubectl describe pod pod-nodeaffinity-required -n dev

Warning FailedScheduling 2m default-scheduler 0/3 nodes are available: 1 node(s) had untolerated taint {node-role.kubernetes.io/control-plane: }, 2 node(s) didn't match Pod's node affinity/selector. preemption: 0/3 nodes are available: 3 Preemption is not helpful for scheduling...

相关推荐
2501_926978331 小时前
分形时空理论框架:从破缺悖论到意识宇宙的物理学新范式引言(理论概念版)--AGI理论系统基础1.1
java·服务器·前端·人工智能·经验分享·agi
弹简特1 小时前
【JavaEE08-后端部分】SpringMVC03-SpringMVC第二大核心处理请求之Cookie/Session和获取header
java·spring boot·spring·java-ee
追随者永远是胜利者1 小时前
(LeetCode-Hot100)10. 正则表达式匹配
java·算法·leetcode·go
追随者永远是胜利者2 小时前
(LeetCode-Hot100)17. 电话号码的字母组合
java·算法·leetcode·职场和发展·go
独自破碎E2 小时前
BISHI53 [P1080] 国王游戏(简化版)
android·java·游戏
坚持就完事了2 小时前
Java中的异常
java·开发语言
~央千澈~2 小时前
抖音弹幕游戏开发之第11集:礼物触发功能·优雅草云桧·卓伊凡
java·前端·python
wuqingshun3141592 小时前
说一下HashMap和HashTable的区别
java·开发语言
DeeplyMind2 小时前
第18章 Docker Compose基础
docker·容器·eureka