集群节点故障时Statefulset与Deployment会有哪些不同的行为

Kubernetes是一个容器平台,制定处理节点故障案例的策略已成为重要标准。要实现这样的蓝图,需要了解节点发生故障时不同控制器的行为。在此文章中,我们将研究发生节点故障时状态集statefulset与部署集Deployment的不同行为。

节点发生故障Deployment控制器会发生什么?

定义:在Kubernetes中,不可达节点被称为分区节点partitioned node,为了了解操作方法,让我们创建一个分区节点方案并了解其行为。

通过Kind创建一个临时的K8s集群

所考虑的示例集群具有一个主节点和3个工作节点。创建具有2个副本的Nginx部署。这些副本在不同的节点上运行;kind-worker2kind-worker3图1捕获了示例集群的状态。

图1: 示例集群的状态

创建一个节点分区。

创建节点分区的一种简单方法是删除节点的IP地址。那就是在kind-worker2上所做的。图2提供了必要的步骤。

创建分区节点

Kubernetes系统的表现如何?

work节点kind-worker2)立即设置为NotReady状态,但pod继续运行。原因是,负责节点的kube-controller-manager的节点控制器部分等待pod-eviction-timeout,以确保在计划将pod删除之前完全无法访问该节点。

pod-eviction-timeout默认设置为5分钟,并在kube-controller-manager启动过程中进行了修改。

在pod逐出超时时间间隔(在本例中为5分钟)之后,节点控制器将在分区节点上运行的pod调度为Termination状态。kube-controller-manager的Deployment Controller部分开始在其他的节点上创建新的副本replicas和调度schedules。在我们的示例中,在kind-worker节点上创建了一个Nginx副本。

图3捕获了Kubernetes系统上的所有状态更改。

Master节点运行Pod的状态.

在分区节点节点上运行的Pod会发生什么?

让我们进入分区节点内,看看发生了什么。从图4中,我们可以观察到原来的pod正在继续运行。是不是有趣!。原因是API服务器无法与分区节点的Kubelet通信以删除Pod。同样,Kubelet也不知道决定要运行哪些Pod的控制器。

Pod继续在分区的工作节点上运行

一旦分区节点加入集群,即可删除pod。下面我们通过一张图总结一下集群中节点发生故障后k8s集群和Deployment控制器触发的工作流程

图5:节点发生故障时部署如何工作的流程图

节点发生故障,Statefulset控制器会发生什么?

与前面的实验一样,依旧通过Kind初始化一个集群,然后使用statefulset创建一个2副本的状态集,这些副本在不同的节点上运行,图6捕获了示例种类群集的状态

图6:示例集群

创建节点故障

创建节点故障方案的另一种简单方法是删除kind-worker2。图7提供了所需的步骤。

图7:捕获创建节点故障的步骤

Kubernetes系统的行为如何?

work节点kind-worker2立即设置为NotReady状态,但pod继续运行。在将pod设置为Termination状态之前,系统等待pod-eviction-timeout间隔s(默认值为5分钟)。

令我们惊讶的是,没有为Statefulsets创建新的pod,而在类似情况下,新的副本被复制用于Deployment部署集。图8捕获了Statefulsets发生节点故障后Kubernetes集群的状态。

图8:节点故障后Nginx状态集的状态

按照Pod-Safety文件,在Kubernetes集群内系统提供了运行保证**,在任何时间点at most one pet。该规则适用于Statefulsets,因为副本被视为pets,而这不适用于Deployment,因为副本被视为cattle。

at most one pet的根本原因是因为有状态集主要用于集群应用程序,这些应用程序有自己的选举主从的方式。在节点故障的情况下,主节点没有足够的信息来确定该节点实际上是故障还是故障是由于网络分区引起的。因此,主机拒绝采取任何措施,从而导致更多问题。主机采用一种实际的方法,减少了一个实例,但以一种可靠的方式工作。

如何从这种dangling state中恢复过来?有几种方法可以处理这种情况,设置terminationGracePeriodSeconds为0的Pod spec。这将确保当节点重新加入群集时,将强制forcefully删除有状态集的容器。这样,Kubernetes主机知道可以保持Pod安全性,因此将启动一个新副本。不利的一面是,pod的关闭显然不是很正常。如果您确定节点确实发生故障或被删除,则可以采用一种自动的方法来检测节点故障并强行删除这些节点。这将确保在可用节点上重新启动有状态集的容器。

关于statefulset控制的有状态pod的相关驱逐问题,也可以参考gitlab issue1gitlab issue2

云原生生态圈版权声明:
作者:云原生生态圈
文章标题: 集群节点故障时Statefulset与Deployment会有哪些不同的行为
链接:https://devopsman.cn/archives/61
来源:云原生生态圈
投稿联系: cloud.native@qq.com 文章版权归作者所有,未经允许请勿转载。
THE END
分享
二维码
打赏
< <上一篇
下一篇>>
文章目录
关闭
目 录