目录
软亲和性策略(preferredDuringSchedulingIgnoredDuringExecution):
硬亲和性策略(requiredDuringSchedulingIgnoredDuringExecution):
自动调度
调度器组件
Kubernetes的调度器(kube-scheduler)是一个独立的控制面组件,负责将Pod调度到合适的节点上。当Pod被创建时,如果Pod的spec.nodeName
字段为空,则表明该Pod需要被调度。此时,kube-scheduler会根据一系列的调度算法和策略来选择一个最佳的节点。
调度流程
Pod的自动调度流程大致可以分为以下几个步骤:
1.监听Pod创建:
kube-scheduler通过监听API Server来发现新创建的且尚未被调度的Pod。
2.过滤(Predicates):
在这个阶段,kube-scheduler会应用一系列的过滤规则来排除不满足Pod调度需求的节点。这些规则包括但不限于:
节点资源是否满足Pod的资源请求(如CPU、内存等)。
节点上是否已存在与Pod端口冲突的Pod。
节点是否设置了Pod无法容忍的污点(Taints)。
节点是否满足Pod的亲和性(Affinity)和反亲和性(Anti-Affinity)要求。
节点是否处于可调度状态(Schedulable)。
3.打分(Priorities):
经过过滤阶段后,会得到一个包含所有可调度节点的列表。在打分阶段,kube-scheduler会根据一系列优先级函数来为这些节点打分。这些优先级函数包括但不限于:
LeastRequestedPriority:优先选择资源利用率最低的节点。
BalancedResourceAllocation:在CPU和内存资源利用率之间寻求平衡。
SelectorSpreadPriority:尽量将Pod分散到不同的节点上,以实现负载均衡。
NodeAffinityPriority:根据Pod的NodeAffinity/NodeSelector要求给节点打分。
TaintTolerationPriority:根据Pod是否能够容忍节点的Taint来给节点打分。
4.选择最优节点:
kube-scheduler会将所有节点的分数进行加权求和,得到每个节点的最终得分。然后,选择得分最高的节点作为Pod的调度目标。如果存在多个得分最高的节点,kube-scheduler会从中随机选取一个。
5.绑定(Binding):
一旦选定了节点,kube-scheduler就会将Pod与选定的节点进行绑定,并将这个调度决定告知API Server。API Server随后会更新Pod的状态,并将其调度到指定的节点上。
定向调度
Pod的定向调度主要有以下几种方式:
NodeName:
通过直接在Pod的YAML文件中指定nodeName字段,将Pod调度到具有该名称的节点上。这种方式跳过了kube-scheduler的调度逻辑,是强制性的。
NodeSelector:
通过为节点和Pod设置标签(Labels),并在Pod的YAML文件中指定nodeSelector字段,选择具有特定标签的节点进行调度。这种方式也是强制性的,如果找不到匹配的节点,Pod将处于Pending状态。
示例:
以下是一个使用nodeName
进行定向调度的Pod YAML文件示例:
apiVersion: v1
kind: Pod
metadata:
name: nginx-1
spec:
containers:
- name: nginx
image: nginx:latest
ports:
- containerPort: 80
nodeName: k8s-node-1 # 指定Pod运行的节点名称
在这个示例中,nodeName
字段被设置为 k8s-node-1
这意味着Pod将被调度到名为 k8s-node-1
的节点上。如果集群中不存在名为 k8s-node-1
的节点,Pod将无法成功调度。
---
使用nodeSelector
进行定向调度的Pod YAML文件示例:
apiVersion: v1
kind: Pod
metadata:
name: nginx-2
spec:
containers:
- name: nginx
image: nginx:latest
ports:
- containerPort: 80
nodeSelector:
disktype: ssd # 选择具有disktype=ssd标签的节点
environment: production # 选择具有environmen