找回密码
立即注册
搜索
热搜: Java Python Linux Go
发回帖 发新帖

1615

积分

1

好友

227

主题
发表于 12 小时前 | 查看: 2| 回复: 0

在 Kubernetes 中,健康检查(Probe) 是保障服务稳定运行的核心能力之一,它能帮助我们更智能地管理应用的生命周期和流量分发。

但在实际生产环境中,Readiness 和 Liveness 这两种探针经常被混用或误用。配置不当轻则导致服务流量抖动,影响用户体验;重则可能引发 Pod 频繁重启,甚至产生服务雪崩的连锁反应。

本文将系统性地解析两者的设计目的、工作机制与核心差异,提供清晰的配置示例与最佳实践,并结合 Spring Boot 应用给出从开发到部署的完整方案。

1、为什么需要 Readiness 和 Liveness 探针?

在没有配置健康检查探针时,Kubernetes 只能感知到一些基础状态:Pod 是否被成功调度、容器进程是否在运行。

然而,这远远不足以判断一个应用是否真正“健康”并准备好提供服务,我们常会遇到以下棘手场景:

  • 应用启动缓慢:例如一个庞大的 Spring Boot 应用,容器状态虽已显示为 Running,但内部的服务、连接池可能仍在初始化。
  • 应用内部卡死:程序可能因死循环、线程死锁或某些阻塞操作而失去响应,但容器进程并未退出。
  • 外部依赖异常:应用所依赖的数据库、Redis 或消息队列暂时不可用,此时若继续接收用户流量,只会返回错误。

Readiness(就绪探针)与 Liveness(存活探针)正是为了精准解决上述问题而设计的两种机制。

2、Readiness Probe:流量守卫者

2.1 核心作用

判断 Pod 是否已经“就绪”,可以安全地接收来自 Service 的流量。

  • 检查失败:Kubernetes 会将此 Pod 从关联的 Service 的 Endpoints 列表中移除。后续的请求将不会被负载均衡到该 Pod。
  • 检查成功:Pod 会被重新加入 Service 的 Endpoints,开始接收流量。
  • ⚠️ 重要特性:Readiness Probe 失败不会导致容器重启。

2.2 典型使用场景

  • 应用启动阶段:等待 Spring Boot 完成上下文初始化、数据源连接建立。
  • 依赖服务异常:当数据库、Redis 或消息中间件连接失败时。
  • 服务自保护状态:当服务触发熔断、限流或主动降级时,应暂时拒绝新流量。
  • 优雅下线流程:配合 lifecycle.preStop 钩子,实现平滑终止。

2.3 示例配置(HTTP 探针)

readinessProbe:
  httpGet:
    path: /actuator/health/readiness
    port: 8080
  initialDelaySeconds: 10  # 容器启动后等待10秒开始第一次探测
  periodSeconds: 5         # 每5秒执行一次探测
  timeoutSeconds: 2        # 探测请求超时时间为2秒
  failureThreshold: 3      # 连续失败3次才标记为不健康

2.4 Spring Boot Readiness 实现示例

Spring Boot 应用中,我们可以自定义健康指示器来精确控制就绪状态。

@Component
public class ReadinessHealthIndicator implements HealthIndicator {
  @Override
  public Health health() {
    if (dbAvailable() && cacheAvailable()) {
      return Health.up().build();
    }
    return Health.down()
                .withDetail("reason", "dependency unavailable")
                .build();
  }
}

逻辑说明

  • 当核心依赖(如数据库、缓存)不可用时,探针返回 DOWN,Pod 会被移出流量池。
  • 应用进程本身保持运行,等待依赖服务恢复。
  • 依赖恢复后,探针自动变更为 UP,Pod 重新接收流量。

3、Liveness Probe:生死判决官

3.1 核心作用

判断容器是否处于“无法自我修复的异常状态”。

  • 检查失败:Kubernetes 会认为该容器已无法恢复,并立即重启容器
  • 检查成功:容器正常运行。

3.2 典型使用场景

  • 进程僵死:如线程死锁,应用完全无响应。
  • 内部故障:死循环、某些关键子系统崩溃导致主功能失效。
  • 资源泄漏:内存泄漏导致应用逐渐卡顿至无响应。

⚠️ 重要提醒
Liveness Probe 不适合 用于检查外部依赖(如数据库)的可用性。否则,一次短暂的网络抖动或数据库维护就可能导致你的应用被不停重启,引发更严重的问题。

3.3 示例配置(HTTP 探针)

livenessProbe:
  httpGet:
    path: /actuator/health/liveness
    port: 8080
  initialDelaySeconds: 60  # 给予应用充足的启动时间
  periodSeconds: 10
  timeoutSeconds: 2
  failureThreshold: 3

3.4 Spring Boot Liveness 示例

@Component
public class LivenessHealthIndicator implements HealthIndicator {
  @Override
  public Health health() {
    if (threadPoolAlive() && mainLoopAlive()) {
      return Health.up().build();
    }
    return Health.down().build();
  }
}

4、Readiness 与 Liveness 核心区别对比

维度 Readiness (就绪探针) Liveness (存活探针)
关注点 能否接收并处理流量 应用进程是否需要重启
失败后果 从 Service Endpoints 中摘除 容器被重启
是否影响 Pod 生命周期
是否适合检查外部依赖 ✅ 是 ❌ 否
是否适合检查内部死锁 ❌ 否 ✅ 是

一句话总结Readiness 控制“流量开关”,Liveness 控制“容器生死”。

5、Readiness + preStop 实现真正的优雅下线

在进行滚动更新或缩容操作时,如果 Pod 被直接删除,正在处理的请求会被强制中断。结合 Readiness Probe 和 preStop 钩子,可以实现流量的平滑迁移与优雅下线,这是构建高可用服务的关键一环。

流程如下

  1. 触发终止:Kubernetes 向 Pod 发送终止信号,并执行 preStop 钩子。
  2. 摘除流量preStop 钩子可先将应用的健康检查端点(如 Readiness)置为失败,使 Pod 立即从 Service 中摘除,不再接收任何新请求
  3. 处理旧请求:等待一段预设时间(如10秒),让 Pod 完成现有请求的处理。
  4. 真正停止:随后容器被正常终止。

示例配置:

apiVersion: v1
kind: Pod
spec:
  containers:
  - name: app
    lifecycle:
      preStop:
        exec:
          command: ["/bin/sh", "-c", "sleep 10"] # 等待10秒处理剩余请求
    readinessProbe:
      httpGet:
        path: /actuator/health/readiness
        port: 8080

通过合理的运维流程与配置,可以极大减少发布和变更期间对用户的影响。

6、结合 Spring Boot Actuator 的完整配置

Spring Boot 2.3+ 版本对 Actuator 的健康端点进行了细化,原生支持独立的 Liveness 和 Readiness 状态,与 Kubernetes 探针理念完美契合。

application.yml 配置

management:
  endpoints:
    web:
      exposure:
        include: health
  health:
    livenessstate:
      enabled: true
    readinessstate:
      enabled: true

配置后,应用会暴露两个端点:

  • GET /actuator/health/liveness: 仅检查应用进程本身是否存活。
  • GET /actuator/health/readiness: 检查应用是否就绪(通常包含对数据库等关键依赖的检查)。

这使得 Spring Boot 应用在 Kubernetes 中的健康检查逻辑更加清晰、职责分明。

7、生产环境探针参数调优指南

参数 建议值 说明
initialDelaySeconds Liveness: 60~120s<br>Readiness: 10~30s 必须大于应用启动时间,避免启动过程中被误杀或误摘。
periodSeconds 5~15s 检查频率。过于频繁会增加应用负担,太慢则会影响故障发现速度。
timeoutSeconds 1~5s 单次探测请求的超时时间。
failureThreshold 3~5 连续失败多少次才判定为最终失败,避免因网络瞬时波动造成误判。

核心调优原则

  • Liveness 要“保守”:设置较长的 initialDelaySeconds 和适当的 failureThreshold,确保只在应用真正“无药可救”时才重启,避免频繁重启引发的雪崩。
  • Readiness 可“积极”:可以相对快速地摘除不健康的 Pod,保护用户体验和系统整体稳定。
  • 结合监控:探针参数需根据应用的实际启动时间、性能表现进行调整,并配合监控系统观察效果。

8、总结

正确地配置和使用 Readiness 与 Liveness 探针,是保障 Kubernetes 应用稳定性的基石。让我们再次回顾核心要点:

  • Readiness 是流量开关,管理 Pod 何时能加入服务网格接收请求。
  • Liveness 是生死判决,管理容器何时应被重启以尝试恢复。
  • 优雅下线依赖于 Readiness Probe 与 preStop 钩子的协同工作。
  • 生产调优的关键在于根据应用特性(如启动速度)合理设置 initialDelaySecondsperiodSeconds 等参数。

深入理解并实践这些概念,你的 云原生 应用将具备更强的自愈能力和更高的可用性。




上一篇:PyTorch实战:多层卷积与全连接网络输出方法详解(图像分类场景)
下一篇:利用AI编程与GitHub+Vercel快速搭建个人网站:零成本部署实战指南
您需要登录后才可以回帖 登录 | 立即注册

手机版|小黑屋|网站地图|云栈社区 ( 苏ICP备2022046150号-2 )

GMT+8, 2025-12-24 17:08 , Processed in 0.200539 second(s), 40 queries , Gzip On.

Powered by Discuz! X3.5

© 2025-2025 云栈社区.

快速回复 返回顶部 返回列表