Kubernetes

K8s 探针机制

·12 分钟阅读·4721 字

StartupProbe、LivenessProbe、ReadinessProbe——原理、配置、区别、实战问题排查

📋 目录

K8s 探针机制

1. 📖 通用基础认知

1.1. 核心执行主体

由节点上的 kubelet 定期发起探测,每个容器独立配置探针(Pod 内多容器互不影响)。

1.2. 三种探测方式(所有探针通用)

三种方式本质都是校验容器是否正常响应,优先级/使用场景不同:

  1. Exec 命令探测
  • 原理:在容器内执行一条命令,判断退出码
  • 规则:退出码 0 → 成功;非0 → 失败
  • 适用:自定义脚本、检查进程、文件、端口等灵活场景
  1. TCP Socket 探测
  • 原理:kubelet 尝试和容器指定端口建立 TCP 连接
  • 规则:连接能建立 → 成功;连不上/超时 → 失败
  • 适用:TCP 服务(MySQL、Redis、后端服务)
  1. HTTP/HTTPS 探测
  • 原理:kubelet 向容器内指定 URL 发送 GET 请求
  • 规则:响应码 200~399 → 成功;4xx/5xx/超时 → 失败
  • 适用:Web 服务、微服务(SpringBoot/Nginx 等,主流用法)

1.3. 通用配置参数(所有探针共用)


## 所有探针都支持以下字段

initialDelaySeconds: 5   # 容器启动后,延迟多久开始第一次探测(秒)

periodSeconds: 10        # 探测间隔,每多久执行一次(默认10s)

timeoutSeconds: 3        # 单次探测超时时间(默认1s)

failureThreshold: 3      # 连续失败多少次,判定为异常(默认3次)

successThreshold: 1      # 连续成功多少次,判定为正常(默认1次)

2. ⚡ 三大探针详解(作用+原理+触发行为+典型配置)

2.1. 启动探针 StartupProbe

2.1.1. 核心作用

专门解决容器启动慢的问题。

部分应用(如 Java、中间件、大数据组件)启动耗时久,还没完成初始化,存活/就绪探针就开始探测,直接误杀容器。

启动探针会阻塞另外两个探针,直到自身探测成功。

2.1.2. 工作原理

  1. 容器启动 → 先只运行 StartupProbe
  2. 启动探针连续成功后 → 探针生命周期结束,才开始执行 Liveness + Readiness
  3. 启动探针持续失败,达到 failureThreshold → kubelet 重启容器

2.1.3. 关键特性

  • 启动探针没有 successThreshold 实际意义,成功一次即完成使命
  • 专为慢启动应用设计(JVM 应用、ES、Kafka、数据库等)
  • 高配置建议:拉长超时、间隔、失败次数,给足启动时间

2.1.4. 示例配置(HTTP 方式)


startupProbe:

  httpGet:

    path: /actuator/health

    port: 8080

  initialDelaySeconds: 10

  periodSeconds: 15

  timeoutSeconds: 10

  failureThreshold: 20  # 最多允许20次失败,总启动时长:10 + 15*20 = 310s

2.2. 存活探针 LivenessProbe

2.2.1. 核心作用

检测容器是否“活着”(进程卡死、僵死、不可用),实现容器自愈重启。

容器进程存在,但内部逻辑卡死、死锁、服务挂死、无响应 → 探针失败,直接重启容器。

2.2.2. 工作原理

  1. 容器启动 + 启动探针完成后,按周期持续探测
  2. 单次探测超时/结果失败 → 计数+1
  3. 连续失败达到 failureThreshold → kubelet 杀死并重启当前容器
  4. 重启后重置所有探针状态

2.2.3. 典型故障场景(探针触发重启)

  • Java 应用死锁、GC 死循环,进程还在但接口无响应
  • Nginx/中间件进程僵死,端口监听正常但不处理请求
  • 容器内部资源耗尽,对外完全无响应

2.2.4. 示例配置(TCP 探测,检查端口)


livenessProbe:

  tcpSocket:

    port: 8080

  initialDelaySeconds: 5

  periodSeconds: 10

  timeoutSeconds: 3

  failureThreshold: 3

2.3. 就绪探针 ReadinessProbe

2.3.1. 核心作用

检测容器是否“准备好接收业务流量”,控制流量转发,不重启容器。

是流量网关,决定 Service/Ingress 是否将请求转发到当前 Pod。

2.3.2. 工作原理

  1. 探测成功 → Pod 状态变为 Ready,Endpoint 列表加入该 Pod,接收流量
  2. 探测失败 → Pod 变为 NotReady,从 Endpoint 中剔除,不再转发新流量
  3. 旧连接默认不会断开,仅拦截新请求;不会重启容器

2.3.3. 核心使用场景

  1. 容器启动完成,但应用还在加载数据、初始化缓存、连接数据库,暂时不能接流量
  2. 应用运行中临时过载、依赖服务宕机,主动摘除流量,避免请求失败
  3. 滚动更新时,保证新 Pod 就绪后再切流量,实现零停机发布

2.3.4. 示例配置(Exec 命令探测)


readinessProbe:

  exec:

    command:

    - sh

    - -c

    - pgrep java  # 检查Java进程是否正常运行

  initialDelaySeconds: 5

  periodSeconds: 10

  timeoutSeconds: 3

  failureThreshold: 3

3. 🔧 三大探针执行顺序 & 整体生命周期(重点)

完整流程:

  1. 容器启动
  2. 等待 initialDelaySeconds → 只执行 StartupProbe
  • 启动探针成功 → 进入下一步
  • 启动探针多次失败 → 重启容器
  1. 启动探针完成 → 同时并行执行 LivenessProbe + ReadinessProbe
  2. 长期运行阶段:
  • Readiness 失败 → 摘流量,Pod NotReady,不重启
  • Liveness 失败 → 直接重启容器,重置所有状态 一句话区分执行逻辑:
    启动探针:等容器跑完初始化
    就绪探针:管流量进不进
    存活探针:管容器死不死、要不要重启

4. ⚙️ 三大探针核心区别对照表

探针类型核心目标探测失败动作影响范围适用场景
StartupProbe
启动探针
等待容器缓慢启动重启容器整个Pod生命周期前置阶段Java、ES、Kafka、数据库等慢启动应用
LivenessProbe
存活探针
检测容器是否僵死重启容器自愈、恢复异常容器进程卡死、死锁、服务无响应
ReadinessProbe
就绪探针
检测容器能否接流量摘除流量,不重启Service/Ingress 流量转发初始化未完成、服务过载、依赖异常

5. 🚀 生产最佳实践 & 避坑指南

5.1. 配置原则

  1. 慢启动应用(Java 为主):必须配 StartupProbe不要单纯靠调大 liveness 的 initialDelaySeconds,启动探针是专门解决方案。
  2. HTTP 服务优先使用 httpGet,标准健康接口 /health / /actuator/health
  3. TCP 服务(MySQL/Redis)优先使用 tcpSocket,简单高效
  4. 自定义复杂检查(脚本、多条件)使用 exec

5.2. 常见坑

5.2.1. 坑1:探针超时/间隔设置过小,导致误杀

  • 现象:业务正常,频繁重启 Pod
  • 原因:探测超时太短、并发高时健康接口响应慢 → 存活探针误判
  • 解决:调大 timeoutSeconds、合理拉长 periodSeconds

5.2.2. 坑2:只配存活探针,不配就绪探针

  • 现象:Pod 启动后立刻进流量,应用还没初始化完成,大量请求报错
  • 解决:线上业务 Pod 建议双探针必配

5.2.3. 坑3:启动探针参数太小,慢应用反复重启

  • 现象:容器一直在重启循环,始终起不来
  • 解决:加大 failureThreshold、periodSeconds,给足启动时间

5.2.4. 坑4:就绪探针失败,以为容器挂了

  • 现象:Pod 状态 NotReady,但容器正常运行、日志无报错
  • 原因:就绪探针失败,仅摘流量,不会重启容器
  • 排查:查看就绪探针日志、健康接口返回值

5.3. 排查命令(线上排障)


## 📖 查看 Pod 事件,探针失败原因

kubectl describe pod <pod-name>

## ⚡ 查看 Pod 状态、Ready 状态

kubectl get pod <pod-name> -o wide

## 🔧 手动进入容器,验证探测命令/接口是否正常

kubectl exec -it <pod-name> -- /bin/sh

6. 🌐 完整 YAML 示例(三合一探针,生产模板)


apiVersion: v1

kind: Pod

metadata:

  name: demo-app

spec:

  containers:

  - name: app

    image: my-java-app:v1

    ports:

    - containerPort: 8080

    # 启动探针:应对Java慢启动

    startupProbe:

      httpGet:

        path: /actuator/health

        port: 8080

      initialDelaySeconds: 10

      periodSeconds: 15

      timeoutSeconds: 10

      failureThreshold: 20

    # 存活探针:卡死就重启

    livenessProbe:

      httpGet:

        path: /actuator/health

        port: 8080

      initialDelaySeconds: 5

      periodSeconds: 10

      timeoutSeconds: 3

      failureThreshold: 3

    # 就绪探针:控制流量

    readinessProbe:

      httpGet:

        path: /actuator/health

        port: 8080

      initialDelaySeconds: 5

      periodSeconds: 10

      timeoutSeconds: 3

      failureThreshold: 3

7. 💾 面试高频简答(精简背诵版)

  1. 三个探针分别作用?
  • 启动探针:等待慢应用完成初始化,避免启动阶段误重启;
  • 存活探针:检测容器僵死,异常则重启容器自愈;
  • 就绪探针:判断容器是否可接收流量,失败则从负载均衡中摘除,不重启容器。
  1. 探针由谁执行?
    节点上的 kubelet 本地执行,不经过 Master 组件。
  2. 就绪探针失败会重启 Pod 吗?
    不会,只会剥离流量,Pod 继续运行。
  3. 为什么 Java 应用建议配置启动探针?
    JVM 启动、类加载、框架初始化耗时较长,直接使用存活探针容易探测失败,导致反复重启。

关联文档

Yanche Blog

记录云原生、Linux、数据库等技术领域的学习心得,以及日常生活的思考与感悟。

© 2026 Yanche Blog. All rights reserved.

Powered by Astro