在 Kubernetes 中使用 Taints 和 Tolerations 进行调度

在 Kubernetes 中,Taints 和 Tolerations 是两个非常重要的概念,它们可以帮助我们在调度 Pod 时,控制哪些节点可以被分配,哪些不能被分配。本文将会对 Taints 和 Tolerations 进行详细介绍,并给出使用场景和示例代码。

Taints 和 Tolerations 是什么?

在 Kubernetes 中,Taints 是一种标记,可以被添加到节点上。每个 Taint 由三部分组成:一个 key、一个 value 和一个 Effect。key 和 value 通常被用于对节点进行分类,而 Effect 则指定了这个 Taint 对节点分配的影响。

在一个节点上,Taint 可以被添加多个,并且不同的 Taint 可以设置不同的 Effect。常见的 Taint Effect 有以下三种:

  • NoSchedule:如果一个节点被添加了 NoSchedule 的 Taint,那么任何没有设置对应 Tolerations 的 Pod 都不能被分配到该节点上。
  • PreferNoSchedule:如果一个节点被添加了 PreferNoSchedule 的 Taint,那么任何没有设置对应 Tolerations 的 Pod 都不会优先被分配到该节点上,但并非不能被分配。
  • NoExecute:如果一个节点被添加了 NoExecute 的 Taint,那么任何没有设置对应 Tolerations 的 Pod 都不能在该节点上运行,同时如果一个已经在该节点上运行的 Pod 没有在对应的时限内设置 Tolerations,那么该 Pod 会被删除。

与 Taint 对应的是 Tolerations,Tolerations 可以被设置在 Pod 上,用于标记哪些节点可以被分配。每个 Tolerations 由两部分组成:一个 key 和一个 operator。如果一个 Tolerations 的 key 与一个节点上的 Taint 的 key 相等并且 operator 相当,那么这个 Pod 就可以被分配到这个节点上。

在 Pod 中设置 Tolerations 时,还可以设置效果的时限,可以指定一个过渡时间,在这个时间内,即使一个节点被添加了 NoExecute 的 Taint,如果一个已经在该节点上运行的 Pod 设置了对应的 Tolerations,那么这个 Pod 也不会被删除。

Taints 和 Tolerations 的使用场景

Taints 和 Tolerations 通常被用于以下三种情况:

  1. 在一个集群中,有一些节点的硬件配置比其他节点要好,我们希望将一些高负载的 Pod 分配到这些节点上。可以通过在这些节点上添加 Taint,并在一些需要用到这些节点的 Pod 上设置对应的 Tolerations。

  2. 在一个集群中,有一些节点是专门用于运行一些调试或测试的任务,这些任务通常比较占用资源,为了避免影响正式任务的运行,可以给这些节点添加一些 Taint 并设置对应的 Tolerations,在调试或测试任务中设置这些 Tolerations。

  3. 在集群中有一些节点用于管理任务,如 etcd、kube-apiserver,通常不希望其他任务被分配到这些节点上,可以设置 NoSchedule 的 Taint 来避免这个问题。

Taints 和 Tolerations 的实践

下面我们将通过一个例子来讲解如何在 Kubernetes 中使用 Taints 和 Tolerations 进行调度。

首先我们需要创建一个集群,这里使用 Minikube 来创建一个本地测试集群:

-------- ----- ------ - -------- --

然后我们可以通过 kubectl 命令来添加一个 Taint,给当前运行的节点添加一个 key 为 "special",value 为 "true",Effect 为 "NoSchedule" 的 Taint:

------- ----- ----- --------- --- ----- ---------------------------------------- -----------------------

这里我们选择给当前唯一的节点添加 Taint,这个 Taint 的作用是禁止运行没有设置对应 Tolerations 的 Pod。

接下来我们创建一个包含 Tolerations 的 Pod,并进行测试:

----------- --
----- ---
---------
  ----- ---------------
-----
  -----------
  - ----- -----
    ------ ------------
  ------------
  - ---- ---------
    --------- -------
    ------ ------
    ------- ------------

在上面的 YAML 文件中,我们定义了一个 Pod,给这个 Pod 增加一个 Tolerations,这个 Tolerations 的 key 等于上面添加 Taint 时的 key,而且它的 operator 和 value 分别等于上面添加 Taint 时的 operator 和 value,即它可以被分配到被添加了 Taint 的节点上。

通过 kubectl apply 命令来创建该 Pod:

------- ----- -- --------------------

然后我们可以通过 kubectl get pod 查看该 Pod 的状态,可以看到该 Pod 已经被分配到了被添加了 Taint 的节点上:

----               -----   ------    --------   ---
---------------    ---     -------   -          --

如果我们尝试创建一个没有设置 Tolerations 的 Pod,可以看到该 Pod 会被调度到一个没有被 Taint 的节点上:

----------- --
----- ---
---------
  ----- ------------------
-----
  -----------
  - ----- -----
    ------ ------------

使用 kubectl apply 创建该 Pod,然后通过 kubectl get pod 查看状态:

----                   -----   ------     --------   ---
------------------     ---     -------    -          ---
---------------        ---     -------    -          ---

可以看到该 Pod 已经被成功调度到了没有被 Taint 的节点上。

总结

本文对 Kubernetes 中的 Taints 和 Tolerations 进行了详细的介绍,并给出了具体的使用场景和示例代码。在实际的项目中,Taints 和 Tolerations 可以帮助我们实现更精细的调度策略,避免资源的浪费和任务的阻塞。如果你对 Kubernetes 的调度机制感兴趣,Taints 和 Tolerations 的深入学习是非常值得推荐的。

来源:JavaScript中文网 ,转载请注明来源 本文地址:https://www.javascriptcn.com/post/66470cbfd3423812e454b74d