Pod phase
Pod 的 status
定义在 PodStatus 对象中,其中有一个 phase
字段。
Pod 的运行阶段(phase)是 Pod 在其生命周期中的简单宏观概述。该阶段并不是对容器或 Pod 的综合汇总,也不是为了做为综合状态机。
Pod 相位的数量和含义是严格指定的。除了本文档中列举的内容外,不应该再假定 Pod 有其他的 phase
值。
下面是 phase
可能的值:
- 挂起(Pending):Pod 已被 Kubernetes 系统接受,但有一个或者多个容器镜像尚未创建。等待时间包括调度 Pod 的时间和通过网络下载镜像的时间,这可能需要花点时间。
- 运行中(Running):该 Pod 已经绑定到了一个节点上,Pod 中所有的容器都已被创建。至少有一个容器正在运行,或者正处于启动或重启状态。
- 成功(Succeeded):Pod 中的所有容器都被成功终止,并且不会再重启。
- 失败(Failed):Pod 中的所有容器都已终止了,并且至少有一个容器是因为失败终止。也就是说,容器以非0状态退出或者被系统终止。
未知(Unknown):因为某些原因无法取得 Pod 的状态,通常是因为与 Pod 所在主机通信失败。
Pod conditions
Pod 有一个 PodStatus 对象,其中包含一个 PodCondition 数组。
每个PodCondition数组的元素都有以下6个字段:lastProbeTime
提供了Pod condition上一次被探测的时间戳lastTransitionTime
提供了改Pod上一次状态装换的时间戳。message
记录了人类可读的状态转换的具体信息。reason
是一个唯一的,一个单词的,CamelCase风格的为了记录condition上一次装换的原因。status
是一个string, 可能的值有“True
”, “False
”, 和 “Unknown
”.type
是一个字符串,有以下值:PodScheduled
: Pod已经被调度到一个节点;Ready
: 已经可以接收请求和应该被加入到所有的匹配的Service的LB池子中;Initialized
: 所有的 init containers 都已经启动成功;ContainersReady
: Pod中所有的容器都已经Ready。
容器探针
探针 是由 kubelet 对容器执行的定期诊断。要执行诊断,kubelet 调用由容器实现的 Handler。有三种类型的处理程序:
- ExecAction:在容器内执行指定命令。如果命令退出时返回码为 0 则认为诊断成功。
- TCPSocketAction:对指定端口上的容器的 IP 地址进行 TCP 检查。如果端口打开,则诊断被认为是成功的。
- HTTPGetAction:对指定的端口和路径上的容器的 IP 地址执行 HTTP Get 请求。如果响应的状态码大于等于200 且小于 400,则诊断被认为是成功的。
每次探测都将获得以下三种结果之一:
- 成功:容器通过了诊断。
- 失败:容器未通过诊断。
- 未知:诊断失败,因此不会采取任何行动。
Kubelet 可以选择是否执行在容器上运行的三种探针执行和做出反应:
livenessProbe
:指示容器是否正在运行。如果存活探测失败,则 kubelet 会杀死容器,并且容器将受到其 重启策略 的影响。如果容器不提供存活探针,则默认状态为Success
。readinessProbe
:指示容器是否准备好服务请求。如果就绪探测失败,端点控制器将从与 Pod 匹配的所有 Service 的端点中删除该 Pod 的 IP 地址。初始延迟之前的就绪状态默认为Failure
。如果容器不提供就绪探针,则默认状态为Success
。startupProbe
: 指示容器中的应用是否已经启动。如果提供了启动探测(startup probe),则禁用所有其他探测,直到它成功为止。如果启动探测失败,kubelet 将杀死容器,容器服从其重启策略进行重启。如果容器没有提供启动探测,则默认状态为成功Success
。该什么时候使用存活(liveness)和就绪(readiness)探针?
如果容器中的进程能够在遇到问题或不健康的情况下自行崩溃,则不一定需要存活探针; kubelet 将根据 Pod 的
restartPolicy
自动执行正确的操作。
如果您希望容器在探测失败时被杀死并重新启动,那么请指定一个存活探针,并指定restartPolicy
为 Always 或 OnFailure。
如果要仅在探测成功时才开始向 Pod 发送流量,请指定就绪探针。在这种情况下,就绪探针可能与存活探针相同,但是 spec 中的就绪探针的存在意味着 Pod 将在没有接收到任何流量的情况下启动,并且只有在探针探测成功后才开始接收流量。
如果您希望容器能够自行维护,您可以指定一个就绪探针,该探针检查与存活探针不同的端点。
请注意,如果您只想在 Pod 被删除时能够排除请求,则不一定需要使用就绪探针;在删除 Pod 时,Pod 会自动将自身置于未完成状态,无论就绪探针是否存在。当等待 Pod 中的容器停止时,Pod 仍处于未完成状态。该什么时候使用startup probe?
FEATURE STATE:
Kubernetes v1.16 [alpha]
如果您的容器通常在超过initialDelaySeconds + failureThreshold×seconds
的时间内启动,那么您应该指定一个startup probe,它检查与liveness probe相同的端点。periodSeconds
的默认值是30秒。然后,您应该将其failureThreshold
设置得足够高,以允许容器启动,而不需要更改liveness probe的默认值。这有助于防止死锁。
For more information about how to set up a liveness, readiness, startup probe, see Configure Liveness, Readiness and Startup Probes.Pod 和容器状态
有关 Pod 容器状态的详细信息,请参阅 PodStatus 和 ContainerStatus。请注意,报告的 Pod 状态信息取决于当前的 ContainerState。
容器状态
一旦Pod被调度到某一个节点,kubelet会使用容器运行时创建容器。容器有三种可能的状态:Waiting/Running/Terminated。可以使用kubectl describe pod [POD_NAME]来检查容器状态。该Pod的每个容器的状态都被显示出来。
Waiting
: 默认的容器状态。如果一个容器不是Running或者Terminated状态,那就是Wating状态。处于等待状态的容器仍然运行其所需的操作,如pull image, apply Secrets等。与此状态一起显示的还有关于此状态的消息和原因,以提供更多信息。...
State: Waiting
Reason: ErrImagePull
...
Running
: 指示容器执行时没有问题。postStart钩子(如果有的话)在容器进入运行状态之前执行。此状态还显示容器进入运行状态的时间。...
State: Running
Started: Wed, 30 Jan 2019 16:46:38 +0530
...
Terminated
: 指示容器完成其执行并停止运行。当容器成功完成执行或由于某种原因失败时,它就会进入这个状态。无论如何,都会显示原因和退出代码,以及容器的启动和完成时间。在容器进入此状态之前,执行preStop钩子(如果有的话)。...
State: Terminated
Reason: Completed
Exit Code: 0
Started: Wed, 30 Jan 2019 11:45:26 +0530
Finished: Wed, 30 Jan 2019 11:45:26 +0530
...
Pod readiness
FEATURE STATE:
Kubernetes v1.14 [stable]
Your application can inject extra feedback or signals into PodStatus: Pod readiness. To use this, setreadinessGates
in the PodSpec to specify a list of additional conditions that the kubelet evaluates for Pod readiness.
Readiness gates are determined by the current state ofstatus.condition
fields for the Pod. If Kubernetes cannot find such a condition in thestatus.conditions
field of a Pod, the status of the condition is defaulted to “False
”. Below is an example:
Here is an example:kind: Pod
...
spec:
readinessGates:
- conditionType: "www.example.com/feature-1"
status:
conditions:
- type: Ready # a built in PodCondition
status: "False"
lastProbeTime: null
lastTransitionTime: 2018-01-01T00:00:00Z
- type: "www.example.com/feature-1" # an extra PodCondition
status: "False"
lastProbeTime: null
lastTransitionTime: 2018-01-01T00:00:00Z
containerStatuses:
- containerID: docker://abcd...
ready: true
...
The Pod conditions you add must have names that meet the Kubernetes label key format.
Status for Pod readiness
The
kubectl patch
command does not support patching object status. To set thesestatus.conditions
for the pod, applications and operators should use thePATCH
action. You can use a Kubernetes client library to write code that sets custom Pod conditions for Pod readiness.
For a Pod that uses custom conditions, that Pod is evaluated to be ready only when both the following statements apply:All containers in the Pod are ready.
- All conditions specified in
ReadinessGates
areTrue
.
When a Pod’s containers are Ready but at least one custom condition is missing or False
, the kubelet sets the Pod’s condition to ContainersReady
.
重启策略
PodSpec 中有一个 restartPolicy
字段,可能的值为 Always、OnFailure 和 Never。默认为 Always。 restartPolicy
适用于 Pod 中的所有容器。restartPolicy
仅指通过同一节点上的 kubelet 重新启动容器。失败的容器由 kubelet 以五分钟为上限的指数退避延迟(10秒,20秒,40秒…)重新启动,并在成功执行十分钟后重置。如 Pod 文档 中所述,一旦绑定到一个节点,Pod 将永远不会重新绑定到另一个节点。
Pod 的一生
通常,pod会一直保留到人工或控制器进程显式地删除它们为止。当Pod的数量超过配置的阈值(由kube-controller-manager
中的end -pod-gc-threshold
决定)时,控制平面将清理已终止的Pod(阶段为成功或失败)。这避免了在创建和终止pod时出现资源泄漏。
有三种可用的控制器:
- 使用 Job 运行预期会终止的 Pod,例如批量计算。Job 仅适用于重启策略为
OnFailure
或Never
的 Pod。 - 对预期不会终止的 Pod 使用 ReplicationController、ReplicaSet 和 Deployment ,例如 Web 服务器。 ReplicationController 仅适用于具有
restartPolicy
为 Always 的 Pod。 - 提供特定于机器的系统服务,使用 DaemonSet 为每台机器运行一个 Pod 。
所有这三种类型的控制器都包含一个 PodTemplate。建议创建适当的控制器,让它们来创建 Pod,而不是直接自己创建 Pod。这是因为单独的 Pod 在机器故障的情况下没有办法自动复原,而控制器却可以。
如果节点死亡或与集群的其余部分断开连接,则 Kubernetes 将应用一个策略将丢失节点上的所有 Pod 的 phase
设置为 Failed。
示例
高级 liveness 探针示例
liveness probe由 kubelet 来执行,因此所有的请求都在 kubelet 的网络命名空间中进行。
apiVersion: v1
kind: Pod
metadata:
labels:
test: liveness
name: liveness-http
spec:
containers:
- args:
- /server
image: k8s.gcr.io/liveness
livenessProbe:
httpGet:
# 当没有定义 "host" 时,使用 "PodIP"
# host: my-host
# 当没有定义 "scheme" 时,使用 "HTTP" scheme 只允许 "HTTP" 和 "HTTPS"
# scheme: HTTPS
path: /healthz
port: 8080
httpHeaders:
- name: X-Custom-Header
value: Awesome
initialDelaySeconds: 15
timeoutSeconds: 1
name: liveness
状态示例
- Pod 中只有一个容器并且正在运行。容器成功退出。
- 记录完成事件。
- 如果
restartPolicy
为:- Always:重启容器;Pod
phase
仍为 Running。 - OnFailure:Pod
phase
变成 Succeeded。 - Never:Pod
phase
变成 Succeeded。
- Always:重启容器;Pod
- Pod 中只有一个容器并且正在运行。容器退出失败。
- 记录失败事件。
- 如果
restartPolicy
为:- Always:重启容器;Pod
phase
仍为 Running。 - OnFailure:重启容器;Pod
phase
仍为 Running。 - Never:Pod
phase
变成 Failed。
- Always:重启容器;Pod
- Pod 中有两个容器并且正在运行。有一个容器退出失败。
- 记录失败事件。
- 如果 restartPolicy 为:
- Always:重启容器;Pod
phase
仍为 Running。 - OnFailure:重启容器;Pod
phase
仍为 Running。 - Never:不重启容器;Pod
phase
仍为 Running。
- Always:重启容器;Pod
- 如果有一个容器没有处于运行状态,并且两个容器退出:
- 记录失败事件。
- 如果
restartPolicy
为:- Always:重启容器;Pod
phase
仍为 Running。 - OnFailure:重启容器;Pod
phase
仍为 Running。 - Never:Pod
phase
变成 Failed。
- Always:重启容器;Pod
- Pod 中只有一个容器并处于运行状态。容器运行时内存超出限制:
- 容器以失败状态终止。
- 记录 OOM 事件。
- 如果
restartPolicy
为:- Always:重启容器;Pod
phase
仍为 Running。 - OnFailure:重启容器;Pod
phase
仍为 Running。 - Never: 记录失败事件;Pod
phase
仍为 Failed。
- Always:重启容器;Pod
- Pod 正在运行,磁盘故障:
- 杀掉所有容器。
- 记录适当事件。
- Pod
phase
变成 Failed。 - 如果使用控制器来运行,Pod 将在别处重建。
- Pod 正在运行,其节点宕机。
- 节点控制器等待直到超时。
- 节点控制器将 Pod
phase
设置为 Failed。 - 如果是用控制器来运行,Pod 将在别处重建。