【问题标题】:Are Kubernetes liveness probe failures voluntary or involuntary disruptions?Kubernetes 活性探测失败是自愿还是非自愿中断?
【发布时间】:2021-07-20 09:09:16
【问题描述】:

我有一个应用程序部署到 Kubernetes,它依赖于外部应用程序。有时这两个之间的连接会进入无效状态,这只能通过重新启动我的应用程序来修复。

为了自动重启,我配置了一个活动探针来验证连接。

这一直很好用,但是,我担心如果那个外部应用程序出现故障(这样连接错误不仅仅是由于 pod 状态无效),我的所有 pod 都会立即重新启动,并且我的应用程序将变得完全不可用。我希望它继续运行,以便不依赖于不良服务的功能可以继续运行。

我想知道吊舱中断预算是否会防止这种情况发生,因为它会由于“自愿”中断而限制吊舱的数量。但是,K8s 文档没有说明活性探测失败是否是自愿中断。是吗?

【问题讨论】:

  • 将外部应用程序迁移到您的 Kubernetes 集群是否可行?这不会直接回答您的问题,但我认为您可以查看以下文章:123
  • @DawidKruk 不幸的是,外部应用程序是 Azure CosmosDB,它没有适合我所处环境的最佳客户端驱动程序。但是,我在使用 ioredis 连接到我自己时遇到了类似的问题-hosted Redis 集群,所以我来看看。谢谢!

标签: kubernetes livenessprobe


【解决方案1】:

我会说,根据文档:

自愿和非自愿中断

在有人(人或控制器)破坏它们或出现不可避免的硬件或系统软件错误之前,Pod 不会消失。

我们将这些不可避免的情况非自愿中断称为应用程序。例如:

  • 支持节点的物理机出现硬件故障
  • 集群管理员误删除虚拟机(实例)
  • 云提供商或管理程序故障导致虚拟机消失
  • 内核恐慌
  • 由于集群网络分区,节点从集群中消失
  • 由于节点为 out-of-resources 而驱逐 pod。

除了资源不足的情况,大多数用户都应该熟悉所有这些情况;它们并非特定于 Kubernetes。

我们将其他情况称为自愿中断。其中包括由应用程序所有者发起的操作和由集群管理员发起的操作。典型的应用程序所有者操作包括:

  • 删除管理 Pod 的部署或其他控制器
  • 更新部署的 pod 模板导致重启
  • 直接删除 pod(例如意外)

集群管理员操作包括:

  • Draining a node 进行维修或升级。
  • 从集群中耗尽节点以缩小集群(了解Cluster Autoscaling)。
  • 从节点中删除一个 pod 以允许其他内容适合该节点。

-- Kubernetes.io: Docs: Concepts: Workloads: Pods: Disruptions

所以你的例子完全不同,据我所知,这既不是自愿的也不是非自愿的。


还可以查看另一个 Kubernetes 文档:

Pod 寿命

与单个应用程序容器一样,Pod 被认为是相对短暂(而不是持久)的实体。 Pod 被创建,分配一个唯一的 ID (UID),并被调度到节点上,直到终止(根据重启策略)或删除。如果 Node 死掉了,那么在超时后调度到该节点的 Pod 将是 scheduled for deletion

Pod 本身不会自我修复。如果一个 Pod 被调度到一个 node 然后失败了,这个 Pod 被删除;同样,由于缺乏资源或节点维护,Pod 将无法生存。 Kubernetes 使用更高级别的抽象,称为 controller,它处理管理相对一次性 Pod 实例的工作。

-- Kubernetes.io: Docs: Concepts: Workloads: Pods: Pod lifecycle: Pod lifetime

容器探测

kubelet 可以选择性地对正在运行的容器执行三种探测并做出反应(专注于livenessProbe):

  • livenessProbe:表示容器是否正在运行。如果 liveness 探测失败,kubelet 会杀死容器,容器会受到其restart policy 的影响。如果 Container 不提供 liveness probe,则默认状态为 Success

-- Kubernetes.io: Docs: Concepts: Workloads: Pods: Pod lifecycle: Container probes

什么时候应该使用活性探针?

如果容器中的进程在遇到问题或变得不健康时能够自行崩溃,则不一定需要活性探测; kubelet 会根据 Pod 的restartPolicy 自动执行正确的操作。

如果您希望您的容器在探测失败时被终止并重新启动,请指定一个活跃度探测,并指定一个 restartPolicy 为 Always 或 OnFailure。

-- Kubernetes.io: Docs: Concepts: Workloads: Pods: Pod lifecycle: When should you use a startup probe

根据这些信息,最好创建自定义活性探针,该探针应考虑内部进程健康检查和外部依赖(活性)健康检查。在第一种情况下,您的容器应该停止/终止您的进程,这与第二种情况不同,具有外部依赖关系。

回答以下问题:

我想知道吊舱中断预算是否会阻止这种情况发生。

在这种特殊情况下,PDB 将无济于事。


我认为让评论更加可见,我在这件事上提供了额外的资源,可能对其他社区成员有用:

【讨论】:

    【解决方案2】:

    使用 PodDisruptionBudget 进行测试。 Pod 仍会同时重启。

    示例

    https://github.com/AlphaWong/PodDisruptionBudgetAndPodProbe

    所以是的。像@Dawid Kruk 一样,你应该创建一个自定义脚本,如下所示

    # something like this
    livenessProbe:
      exec:
        command:
        - /bin/sh
        - -c
        # generate a random number for sleep
        - 'SLEEP_TIME=$(shuf -i 2-40 -n 1);sleep $SLEEP_TIME; curl -L --max-time 5 -f nginx2.default.svc.cluster.local'
      initialDelaySeconds: 10
      # think about the gap between each call
      periodSeconds: 30
      # it is required after k8s v1.12
      timeoutSeconds: 90
    

    【讨论】:

      【解决方案3】:

      我想知道吊舱中断预算是否会阻止这种情况发生。

      是的,它会阻止。

      正如您所说,当 pod 出现故障(或节点故障)时,Pod 无法使用。但是,某些服务要求始终保持最少数量的 pod 始终运行。

      可能还有另一种方式 (Stateful resource),但它是可用的最简单的 Kubernetes 资源之一。

      注意:您还可以在minAvailable 字段中使用百分比而不是绝对数字。例如,您可以声明所有带有 app=run-always 标签的 Pod 中的 60% 需要始终运行。

      【讨论】:

      • OP 询问有关自愿中断的问题。从他们的问题来看,他们似乎已经了解 PDB。
      • 是的,他们知道,但根据他的要求。这是实现的最小努力。我编辑了我的答案。让他回来分享他的意见。此外,这需要新的研究而不是直接的答案。同意吗?
      • “是的,它会阻止。” --- 你确定 PDB 会阻止 liveness probe 重新启动 pod 吗?
      • @Gupta 我需要同意你的最后评论。您能否编辑您的答案以支持您所做的最后评论(loose-loose 情况),以便更明显并更清楚地解释情况?
      • 编辑评论- 我不是那个意思。这是需要在应用程序级别处理的事情。一方面,PDB 尝试根据其实现的性质使 pod 准备好,另一方面,Liveness Probe 将尝试重新启动 pod 以使其健康。
      猜你喜欢
      • 2011-07-07
      • 2023-03-11
      • 1970-01-01
      • 2014-03-13
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-11-25
      相关资源
      最近更新 更多