kubernetes-guide/troubleshooting/pod/healthcheck-failed.md

39 lines
2.6 KiB
Markdown
Raw Normal View History

2023-09-27 17:04:00 +08:00
# 排查健康检查失败
* Kubernetes 健康检查包含就绪检查(readinessProbe)和存活检查(livenessProbe)
* pod 如果就绪检查失败会将此 pod ip 从 service 中摘除,通过 service 访问,流量将不会被转发给就绪检查失败的 pod
* pod 如果存活检查失败kubelet 将会杀死容器并尝试重启
健康检查失败的可能原因有多种除了业务程序BUG导致不能响应健康检查导致 unhealthy还能有有其它原因下面我们来逐个排查。
## 健康检查配置不合理
`initialDelaySeconds` 太短,容器启动慢,导致容器还没完全启动就开始探测,如果 successThreshold 是默认值 1检查失败一次就会被 kill然后 pod 一直这样被 kill 重启。
## 节点负载过高
cpu 占用高(比如跑满)会导致进程无法正常发包收包,通常会 timeout导致 kubelet 认为 pod 不健康。参考 [排查节点高负载](../node/node-high-load.md) 。
## 容器进程被木马进程杀死
参考 [使用 systemtap 定位疑难杂症](../skill/use-systemtap-to-locate-problems.md) 进一步定位。
## 容器内进程端口监听挂掉
使用 `netstat -tunlp` 检查端口监听是否还在,如果不在了,抓包可以看到会直接 reset 掉健康检查探测的连接:
```bash
20:15:17.890996 IP 172.16.2.1.38074 > 172.16.2.23.8888: Flags [S], seq 96880261, win 14600, options [mss 1424,nop,nop,sackOK,nop,wscale 7], length 0
20:15:17.891021 IP 172.16.2.23.8888 > 172.16.2.1.38074: Flags [R.], seq 0, ack 96880262, win 0, length 0
20:15:17.906744 IP 10.0.0.16.54132 > 172.16.2.23.8888: Flags [S], seq 1207014342, win 14600, options [mss 1424,nop,nop,sackOK,nop,wscale 7], length 0
20:15:17.906766 IP 172.16.2.23.8888 > 10.0.0.16.54132: Flags [R.], seq 0, ack 1207014343, win 0, length 0
```
连接异常,从而健康检查失败。发生这种情况的原因可能在一个节点上启动了多个使用 `hostNetwork` 监听相同宿主机端口的 Pod只会有一个 Pod 监听成功,但监听失败的 Pod 的业务逻辑允许了监听失败并没有退出Pod 又配了健康检查kubelet 就会给 Pod 发送健康检查探测报文,但 Pod 由于没有监听所以就会健康检查失败。
## SYN backlog 设置过小
SYN backlog 大小即 SYN 队列大小,如果短时间内新建连接比较多,而 SYN backlog 设置太小,就会导致新建连接失败,通过 `netstat -s | grep TCPBacklogDrop` 可以看到有多少是因为 backlog 满了导致丢弃的新连接。
如果确认是 backlog 满了导致的丢包,建议调高 backlog 的值,内核参数为 `net.ipv4.tcp_max_syn_backlog`