节点
Kubernetes 通过将容器放入 Pod 中运行在**节点**上,来运行你的工作负载。根据集群的不同,节点可以是虚拟机或物理机。每个节点都由控制平面管理,并包含运行Pod 所需的服务。
通常,一个集群中有多个节点;在学习或资源有限的环境中,你可能只有一个节点。
节点上的组件包括 kubelet、容器运行时和 kube-proxy。
管理
有两种主要方式可以将节点添加到API 服务器:
- 节点上的 kubelet 自行注册到控制平面
- 你(或其他人工用户)手动添加一个 Node 对象
在创建 Node 对象后,或者 kubelet 在节点上自行注册后,控制平面会检查新的 Node 对象是否有效。例如,如果你尝试从以下 JSON 清单创建 Node:
{
"kind": "Node",
"apiVersion": "v1",
"metadata": {
"name": "10.240.79.157",
"labels": {
"name": "my-first-k8s-node"
}
}
}
Kubernetes 在内部创建一个 Node 对象(表示)。Kubernetes 检查是否有 kubelet 注册到与 Node 的 `metadata.name` 字段匹配的 API 服务器。如果节点是健康的(即所有必要的服务都在运行),那么它就具备运行 Pod 的资格。否则,在它变得健康之前,该节点将被忽略,不参与任何集群活动。
Node 对象的名称必须是有效的DNS 子域名。
节点名称的唯一性
名称标识一个节点。两个节点不能同时拥有相同的名称。Kubernetes 还假定具有相同名称的资源是同一个对象。对于节点,它隐式假定使用相同名称的实例将具有相同的状态(例如网络设置、根磁盘内容)和属性(如节点标签)。如果实例在未更改其名称的情况下被修改,这可能会导致不一致。如果节点需要更换或重大更新,则需要先从 API 服务器中删除现有节点对象,然后在更新后重新添加。
节点的自注册
当 kubelet 标志 `—register-node` 为 true(默认值)时,kubelet 将尝试向 API 服务器注册自己。这是首选模式,大多数发行版都使用此模式。
对于自注册,kubelet 以以下选项启动:
`--kubeconfig` - 用于向 API 服务器进行身份验证的凭证路径。
`--cloud-provider` - 如何与云供应商通信以读取其元数据。
`--register-node` - 自动向 API 服务器注册。
`--register-with-taints` - 使用给定的污点列表(逗号分隔的 `
= : `)注册节点。 如果 `register-node` 为 false,则此操作为空。
`--node-ip` - 节点的 IP 地址的可选逗号分隔列表。对于每个地址族,你只能指定一个地址。例如,在单栈 IPv4 集群中,你将此值设置为 kubelet 应为节点使用的 IPv4 地址。有关运行双栈集群的详细信息,请参阅配置 IPv4/IPv6 双栈。
如果你不提供此参数,kubelet 将使用节点的默认 IPv4 地址(如果有);如果节点没有 IPv4 地址,则 kubelet 将使用节点的默认 IPv6 地址。
`--node-labels` - 在集群中注册节点时要添加的标签(参见NodeRestriction 准入插件强制执行的标签限制)。
`--node-status-update-frequency` - 指定 kubelet 将其节点状态发布到 API 服务器的频率。
当节点授权模式和NodeRestriction 准入插件启用时,kubelet 仅被授权创建/修改自己的 Node 资源。
注意
如节点名称唯一性部分所述,当节点配置需要更新时,一个好的做法是重新向 API 服务器注册该节点。例如,如果 kubelet 使用一组新的 `--node-labels` 重新启动,但使用了相同的节点名称,则更改不会生效,因为标签仅在节点向 API 服务器注册时设置(或修改)。
如果节点配置在 kubelet 重启时发生更改,已经在节点上调度的 Pod 可能会出现异常行为或导致问题。例如,已运行的 Pod 可能会被新的节点标签污点,而其他与该 Pod 不兼容的 Pod 将根据新的标签进行调度。节点重新注册确保所有 Pod 都将被排出并正确重新调度。
手动节点管理
你可以使用 kubectl 创建和修改 Node 对象。
当你希望手动创建 Node 对象时,设置 kubelet 标志 `--register-node=false`。
无论 `--register-node` 的设置如何,你都可以修改 Node 对象。例如,你可以在现有 Node 上设置标签或将其标记为不可调度。
你可以通过向节点添加一个或多个 `node-role.kubernetes.io/
Kubernetes 会忽略节点角色的标签值;按照约定,你可以将其设置为与你在标签键中用于节点角色的字符串相同。
你可以将节点上的标签与 Pod 上的节点选择器结合使用,以控制调度。例如,你可以将 Pod 限制为仅有资格在可用节点的一个子集上运行。
将节点标记为不可调度会阻止调度器将新的 Pod 放置在该节点上,但不会影响该节点上现有的 Pod。这在节点重启或其他维护之前的准备步骤中很有用。
要将节点标记为不可调度,请运行
kubectl cordon $NODENAME
有关更多详细信息,请参阅安全地排出节点。
注意
作为DaemonSet一部分的 Pod 能够容忍在不可调度节点上运行。DaemonSet 通常提供节点本地服务,即使节点正在排出工作负载应用程序,这些服务也应在节点上运行。节点状态
节点的 Status 包含以下信息:
你可以使用 `kubectl` 查看节点的 Status 和其他详细信息
kubectl describe node <insert-node-name-here>
有关更多详细信息,请参见节点状态。
节点心跳
Kubernetes 节点发送的心跳有助于你的集群确定每个节点的可用性,并在检测到故障时采取行动。
对于节点,有两种形式的心跳:
节点控制器
节点控制器是一个 Kubernetes 控制平面组件,用于管理节点的各个方面。
节点控制器在节点的生命周期中扮演着多个角色。第一个是在节点注册时为其分配一个 CIDR 块(如果启用了 CIDR 分配)。
第二个是保持节点控制器的内部节点列表与云提供商的可用机器列表同步。在云环境中运行且节点不健康时,节点控制器会询问云提供商该节点的 VM 是否仍然可用。如果不可用,节点控制器会从其节点列表中删除该节点。
第三个是监控节点的健康状况。节点控制器负责:
- 在节点无法访问的情况下,更新 Node 的 `.status` 字段中的 `Ready` 状况。在这种情况下,节点控制器会将 `Ready` 状况设置为 `Unknown`。
- 如果一个节点仍然无法访问:触发对该不可访问节点上所有 Pod 的API 发起的驱逐。默认情况下,节点控制器在将节点标记为 `Unknown` 和提交第一个驱逐请求之间会等待 5 分钟。
默认情况下,节点控制器每 5 秒检查一次每个节点的状态。可以使用 `kube-controller-manager` 组件上的 `--node-monitor-period` 标志配置此周期。
驱逐速率限制
在大多数情况下,节点控制器将驱逐速率限制为每秒 `—node-eviction-rate`(默认 0.1),这意味着它每 10 秒不会从超过 1 个节点驱逐 Pod。
当给定可用区域中的节点不健康时,节点驱逐行为会发生变化。节点控制器会同时检查该区域中不健康的节点百分比(`Ready` 状态为 `Unknown` 或 `False`)。
- 如果健康状况不佳的节点所占比例至少达到 `--unhealthy-zone-threshold`(默认值为 0.55),则会降低驱逐速率。
- 如果集群规模较小(即节点数小于或等于 `--large-cluster-size-threshold`,默认值为 50),则停止驱逐。
- 否则,驱逐速率会降低到每秒 `—secondary-node-eviction-rate`(默认为 0.01)。
这些策略按可用区域实现的原因是,一个可用区域可能与控制平面分离,而其他区域保持连接。如果你的集群不跨多个云提供商可用区域,则驱逐机制不会考虑每个区域的不可用性。
将节点分散到多个可用区域的一个主要原因是,当一个完整的区域宕机时,工作负载可以转移到健康的区域。因此,如果一个区域中的所有节点都不健康,则节点控制器以 `—node-eviction-rate` 的正常速率驱逐。极端情况是所有区域都完全不健康(集群中没有任何节点是健康的)。在这种情况下,节点控制器假定控制平面与节点之间存在连接问题,并且不执行任何驱逐。(如果发生故障并且某些节点重新出现,节点控制器会从剩余的不健康或无法访问的节点中驱逐 Pod)。
节点控制器还负责驱逐运行在带有 `NoExecute` 污点的节点上的 Pod,除非这些 Pod 容忍该污点。节点控制器还会添加与节点问题(如节点无法访问或未准备就绪)相对应的污点。这意味着调度器不会将 Pod 放置在不健康的节点上。
资源容量跟踪
Node 对象跟踪节点的资源容量信息:例如,可用内存量和 CPU 数量。自注册的节点在注册期间报告其容量。如果你手动添加节点,则需要在添加时设置节点的容量信息。
Kubernetes 调度器确保节点上的所有 Pod 都有足够的资源。调度器会检查节点上容器请求的总和是否不大于节点的容量。该请求总和包括 kubelet 管理的所有容器,但不包括由容器运行时直接启动的任何容器,也不包括在 kubelet 控制之外运行的任何进程。
注意
如果你想为非 Pod 进程显式保留资源,请参阅为系统守护进程保留资源。节点拓扑
Kubernetes v1.27 [stable]
(默认启用:true)如果已启用 `TopologyManager` 功能门控,则 kubelet 在做出资源分配决策时可以使用拓扑提示。有关更多信息,请参见控制节点上的拓扑管理策略。
下一步
了解更多信息:
- 构成节点的组件。
- Node 的 API 定义.
- 架构设计文档的节点部分。
- 优雅/非优雅节点关机.
- 节点自动扩缩,用于管理集群中节点的数量和大小。
- 污点和容忍.
- 节点资源管理器.
- Windows 节点的资源管理.