现在我们知道了,服务(service)可以通过服务的 pod 选择器来匹配具有相应标签的 pod。匹配成功后, pod 将作为服务的后端,它将成为服务的一部分,并且请求开始被重定向到 pod。但是,如果 pod 没有完全启动好,比如改 pod 可能需要时间来加载配置或数据,或者可能需要执行预热过程以防止第一个用户请求时间太长影响了用户体验。 在这种情况下,不希望该 pod 立即开始接 收请求,尤其是在有其他运行的 pod 可以正确快速地处理请求的情况下。 不要将请求转发到正在启动的 pod 中,直到完全准备就绪。
就绪探针
前面我们了解了存活探针,以及它们如何通过确保异常容器自动重启来保持应用程序的正常运行。与存活探针类似,Kubernetes 还允许为容器定义准备就绪探针 。
就绪探测器会定期调用,并确定特定的 pod 是否接收客户端请求。当容器的准备就绪探测返回成功时,表示容器己准备好接收请求。
这个准备就绪的概念显然是每个容器特有的东西。 Kubernetes 只能检查在容器中运行的应用程序是否响应一个简单的 GET 请求,或者它可以响应特定的 URL 路径(该 URL 导致应用程序执行一系列检查以确定它是否准备就绪)。考虑到应用程序的具体情况,这种确切的准备就绪的判定是应用程序开发人员的 责任。
像存活探针一样,就绪探针有三种类型:
- HTTP GET 探针对容器的 IP 地址(指定的端口和路径)执行 HTTP GET 请求。如果探测器收到响应,并且响应状态码不代表错误(换句话说,如果 HTTP 响应状态码是 2xx 或 3xx ),则认为探测成功。如果服务器返回错误响应状态码或者根本没有响应,那么探测就被认为是失败的。
- TCP 套接字探针尝试与容器指定端口建立 TCP 连接。如果连接成功建立,则探测成功。反之失败。
- Exec 探针在容器内执行任意命令,并检查命令的退出状态码。如果状态码是 0,则探测成功。所有其他状态码都被认为失败。
了解就绪探针的流程
启动容器时,可以为 Kubernetes 配置一个等待时间,经过等待时间后才可以执行第 一次准备就绪检查。之后,它会周期性地调用探针,并根据就绪探针的结果采取行动。如果某个 pod 报告它尚未准备就绪,则会从该服务(Service)中删除该 pod。如果 pod 再次准备就绪,则重新添加 pod。
与存活探针不同,如果容器未通过准备检查,则不会被终止或重新启动。这是存活探针与就绪探针之间的重要区别。存活探针通过杀死异常的容器并用新的正常容器替代它们来保持 pod 正常工作,而就绪探针确保只有准备好处理请求的 pod 才可以接收请求。这在容器启动时最为必要,当然在容器运行一段时间后也是有用的。
如下图所示,如果一个容器的就绪探测失败, 则将该容器从端点对象中移除。连接到该服务的客户端不会被重定向到 pod。这和 pod 与服务的标签选择器完全不匹配的效果相同。
pod 添加就绪探针
我们可以在定义 pod 模板的时候添加好探针,也可以通过 kubectl edit 命令来修改已存在的 pod 模板。下面我们就来修改之前创建的 ReplicationController中的 pod 模板。
kubectl edit rc rc-test
当在文本编辑器中打开 ReplicationController 的 YAML 时,就将以下就绪探针定义添加到 spec.template.spec.containers 下的容器模板中。修改后的 YAML 大致如下:
apiVersion: v1
kind: ReplicationController
..... ##省略其它
spec:
..... ##省略其它
template:
spec:
containers:
- name: test-rc-nginx
image: nginx
## 添加就绪探针
readinessProbe:
exec:
command:
- ls
- /var/test
..... ##省略其它
就绪探针将定期在容器内执行 ls /var/test 命令。 如果文件存在,则 ls 命令返回退出码 0,否则返回非零的退出码。如果文件存在,则就绪探针为成功,反之失败。
修改 rc 之后,现有的所有 pod 仍没有定义准备就绪探针。我们需要删除现有 pod 并让它们通过修改之后的 ReplicationController 重新创建。新的 pod 将进行就绪检查会一直失败,并且不会将其作为服务的端点,直到在每个 pod 中创建 /var/test 文件。
## 列出 pod 会发现所有的 pod 都处于 NO READY 状态
[root@h249 test]# kc get pods
NAME READY STATUS RESTARTS AGE
rc-test-nxg74 0/1 Running 0 9m55s
rc-test-pztvx 0/1 Running 0 6m58s
rc-test-svkzp 0/1 Running 0 6m58s
使用 kubecl exec 命令为 pod 创建 /var/test 文件
[root@h249 home]# kc exec rc-test-nxg74 -- touch /var/test
准备就绪探针会定期检查,默认情况下每 10 秒检查一次。可能不是马上就会调用就绪探针,因此容器可能还是未准备好。但是最晚 10 秒钟内,该 pod 就会准备就绪。