健康检查
AISIX 为进程、流量、配置和模型状态分别提供健康与状态端点。这些端点同时适用于开源 AISIX 网关和连接 AISIX Cloud 的 AISIX 网关。请使用与所监控条件对应的端点。要验证从调用方到模型服务提供方的完整路径,请通过网关发送测试请求。
| 问题 | 端点 | 监听器 |
|---|---|---|
| 进程是否正在运行且未在关闭? | GET /livez | 代理 |
| 此实例是否应接收代理流量? | GET /readyz | 代理 |
| 此实例是否已应用任何有效配置? | GET /status/ready | 指标/状态 |
| 此实例当前使用什么配置提供服务? | GET /status/config | 指标/状态 |
| 模型是否可用于路由? | GET /status/models | 指标/状态 |
这些端点不需要身份认证。启用 Prometheus 指标时会提供指标/状态端点;默认情况下已启用。请确保该监听器仅对监控和运维系统开放。
代理存活检查
使用 /livez 检查进程存活状态:
curl -i "http://127.0.0.1:3000/livez"
健康进程返回 200 OK,响应体为 ok。在优雅关闭期间,存活检查返回 503 Service Unavailable,使编排和流量系统可以替换或移除该实例。
手动排查时可以追加 ?verbose=1。自动化探针不要依赖 verbose 响应体。
存活检查刻意保持较窄范围。它不能证明网关已经加载配置、模型可用或模型服务提供方请求能够成功。
流量就绪
使用 /readyz 判断实例是否应接收流量:
curl -i "http://127.0.0.1:3000/readyz"
实例正在排空或尚未应用第一个配置时,该端点返回 503 Service Unavailable。有效配置可用后,只要网关仍能使用该配置提供服务,实例就会保持就绪。
控制面或配置存储中断不会仅仅因为最近没有更新就让运行中的网关变为未就绪。来源停滞通常会影响所有实例,将它们全部移出流量会中断流量路径,而不是把流量转移到健康实例。请单独监控配置新鲜度。
排查实例未就绪的原因时可以追加 ?verbose=1。自动化探针不要依赖 verbose 响应体。
在 Kubernetes 中,请将存活和就绪探针分别指向代理监听器上的 /livez 和 /readyz。请为网关留出足够的终止时间,以排空进行中的请求和流式请求。
关闭与排空
负载均衡器是在下一次健康检查时才知道某个实例正在退出的,而不是实例作出决定的那一刻。在这两个时间点之间,它仍然会把新连接路由过来。如果网关一收到关闭信号就关闭监听器,这段间隔内被路由过来的连 接都会被拒绝,调用方在一次普通的滚动更新或缩容中就会看到网关错误。
因此网关把这两件事分开。收到 SIGTERM 或 SIGINT 时,它会:
- 立即让
/readyz和/livez返回503 Service Unavailable,使下一次健康检查将其移出流量。 - 继续接受新连接,至少持续
shutdown.min_drain_secs,默认为 30 秒。 - 为每个 HTTP/1.1 响应加上
Connection: close,使使用连接池的客户端在用完连接后主动退役,而不是把空闲连接一直留着。HTTP/2 客户端会在监听器关闭时收到GOAWAY帧。 - 只有在该窗口结束且没有任何进行中的请求时,才停止接受新连接。
- 随后不设自身期限地处理完剩余的进行中请求,然后退出。
请把 min_drain_secs 设置为大于为该实例做负载均衡的组件的发现延迟。Kubernetes 就绪探针需要 periodSeconds x failureThreshold;外部负载均衡器则需要它自身的检查间隔乘以重试次数。设置过小会在流量仍在到达时关闭监听器;设置过大只会延迟退出。
shutdown:
min_drain_secs: 30
这个窗口是最小值,而不是期限。窗口结束后,网关仍会等待进行中的请求数降为零,因此比配置更慢的负载均衡器无法让它在流量仍在到达时关闭监听器。设为 0 会完全取消该窗口,仅当没有任何组件通过健康检查将流量路由到该实例时才适用。
由于进行中请求的排空没有上限,整个流程的实际上限由部署平台决定——Kubernetes 中是 terminationGracePeriodSeconds,systemd 下是 TimeoutStopSec。请把它设置为大于最长的请求耗时,同时注意 preStop 钩子的执行时间也计入 Kubernetes 的预算。一次推理调用或一个流式响应可能持续数分钟。
请把外部负载均衡器的健康检查指向 /readyz,而不是单纯的 TCP 连接探测。TCP 探测无法观察到就绪状态,它唯一能得到的信号就是监听器关闭——而这正是排空窗口要避免的那个事件。
在日志中观察排空过程
排空过程会记录自身的进展,因为一次请求通常留下的记录是在它结束时才写出的——而在平台的宽限期到期时仍在运行的请求根本走不到那一步。这些日志正是你把网关已经接手的工作,与信号之后仍被路由过来的流量区分开的依据:
| 日志内容 | 字段 | 写出时机 |
|---|---|---|
draining — /readyz now reports 503, still accepting new connections | min_drain_secs、in_flight、open_connections | 收到信号时写出一次。 |
still draining in-flight requests | in_flight、open_connections | 排空期间周期性写出。 |
request arrived while draining | method、path,以及该请求自身的 request_id、peer 和 downstream_request_id | 信号之后每到达一个请求写一条。 |
accepted a new downstream connection while draining | peer、open_connections | 信号之后每接受一条连接写一条。 |
这两个计数回答的是不同的问题,且无法互相推导。in_flight 统计正在处理的请求,流式响应只要还可能有字节流出就一直占着自己的名额;open_connections 统计代理监听器上处于打开状态的下游连接,包含连接池中没有承载请求、正处于空闲的那些。因此,in_flight 一直不降导致排空迟迟不 结束,说明网关在处理自己已经接手的工作;in_flight 已降为零而 open_connections 仍不降,说明客户端握着用不到的连接不放;open_connections 还在上升,则说明仍有组件在往这里路由新连接。
那两条逐事件的日志合起来解释了滚动更新期间失败的请求。一条到达日志若能匹配到 peer 相同的接受日志,说明连接本身是在网关已经请求被摘除之后才被路由过来的——负载均衡器还没跟上,而这正是 min_drain_secs 要吸收的情况。一条到达日志若匹配不到接受日志,说明该连接早于信号存在,是客户端从自己的连接池中复用的,而这正是 Connection: close 响应头负责退役的对象。
不过接受日志本身无法区分你的调用方和你的平台。/livez 和 /readyz 同样由代理监听器提供服务,探针在整个排空期间会持续以各自独立的连接到达,因此它们会抬高 open_connections,也会像其他连接一样产生接受日志。作出这项判断的是到达日志:它知道请求路径,并有意排除这两个探针端点,以免为数不多的真实请求被每隔几秒一次的探针淹没。接受日志则用来看到达日志看不到的情况——一条建立了却从未被使用的连接。
peer 和 downstream_request_id 就是指标与日志中描述的那组连接标识。把它们与网关前置组件自己的记录相互匹配,就能证明一条网关日志和一条负载均衡器日志说的是同一条连接。
配置状态
指标/状态监听器提供两个配置检查。
GET /status/ready 是仅检查配置的启动门禁:
- 应用第一个有效配置之前返回
503 Service Unavailable; - 有效配置可用后返回
200 OK;后续更新失败而 AISIX 使用最后已知的有效快照时也会返回200 OK。
GET /status/config 用于说明 AISIX 观察到和应用的内容:
curl -sS "http://127.0.0.1:9090/status/config"
当资源更新没有反映到代理行为中时,请使用该端点。比较来源状态与已应用状态,然后检查被拒绝的资源和最近一次加载失败。有关完整响应字段、状态含义、Prometheus 指标和告警示例,请参阅配置状态。
配置状态不能替代调用方路径验证。预期快照应用后,请查询 GET /v1/models,并发送行为发生变更的请求。请参阅配置传播。
按模型检查运行时健康状态
当网关已就绪,但路由避开某个模型或报告没有符合条件的目标时,请使用 GET /status/models:
curl -sS "http://127.0.0.1:9090/status/models"
每个已配置模型会报告以下高层状态之一:
healthy:可用于路由;cooldown:在最近的上游失败后暂时移出路由;unhealthy:后台模型检查失败后被排除;not_applicable:可用性由其目标决定的虚拟模型。
状态视图有助于识别冷却和后台检查失败,但不会验证调用方访问权限或模型服务提供方凭证。即使模型报告为健康,调用方 API Key、模型服务提供方密钥或上游响应仍可能导致请求失败。
有关完整响应字段,请参阅配置状态。
组合健康信号
请从最早失败的层级开始排查:
| 信号 | 下一项检查 |
|---|---|
/livez 失败。 | 进程状态、监听器绑定、监听器 TLS 和关闭状态 |
/readyz 失败。 | 排空状态和初始配置可用性 |
/status/ready 失败。 | 初始配置来源和加载错误 |
/status/config 为 degraded 或 out_of_sync。 | 被拒绝的资源、来源连接和 last_failure |
/status/models 报告 cooldown 或 unhealthy。 | 模型服务提供方凭证、提供方可用性、模型检查和出站网络 |
| 所有健康端点均成功,但请求失败。 | 调用方访问权限、模型服务提供方路径、策略执行和上游响应 |
最后,请使用与应用相同的路径进行检查:
AISIX_API_KEY="YOUR_CALLER_API_KEY"
curl -sS "http://127.0.0.1:3000/v1/models" \
-H "Authorization: Bearer ${AISIX_API_KEY}"
然后通过所需的端点和模型发送真实请求。最后这项探测会验证运行时健康端点刻意不检查的条件。
下一步
使用故障排除,将失败的健康检查或请求路径检查进一步定位到配置、调用方策略、AISIX Cloud 投射或上游模型服务提供方。