K8s创建Pod全流程:API Server、Scheduler、Controller、kubelet协作详解

Pod对象写入API Server只是起点。把客户端请求、控制面调度、控制器调谐、节点执行和状态回报串起来,才能解释Pod为什么Pending、为什么卡在ContainerCreating,以及什么证据能证明容器真的运行。

阅读建议: 先区分两个时间点:Pod对象被API Server接受并持久化,和节点上的kubelet已经创建、启动容器。前者说明请求进入了集群控制面,后者才说明工作负载开始在节点执行;中间还隔着调度、控制器调谐、镜像准备、网络与存储等环节。

K8s创建Pod的全流程适合用来排查“命令返回成功但Pod不Running”“Pod长期Pending”或“卡在ContainerCreating”等问题。本文按kubectl / 客户端、API Server、Scheduler、Controller、kubelet和状态回报串起协作链,并给出事件、日志、权限、项目 / 命名空间和删除风险的验证顺序。具体版本行为、准入策略和运行时差异,仍需按目标集群与当前官方文档复核。

K8s创建Pod时客户端、API Server、Scheduler、Controller和kubelet之间的协作顺序
图:K8s创建Pod时客户端、API Server、Scheduler、Controller和kubelet之间的协作顺序

*图:Pod创建要经过请求持久化、调度绑定、控制器调谐、节点执行和状态回报,Pod对象存在不代表容器已运行。*

Pod对象创建与容器运行是两件事

一个Pod清单描述了期望的工作负载对象:容器镜像、命令、资源请求、环境变量、卷、探针和其他策略。通过客户端提交后,集群首先处理的是一个API对象;只有对象被接受、调度到节点并由节点代理执行,容器才可能进入创建和运行阶段。

可以把过程拆成两条线:

  • 控制面对象线。 客户端请求到达API Server,完成认证、授权、准入检查并写入持久化存储;Scheduler可能为未绑定节点的Pod选择节点,Controller则持续比较期望状态和实际状态。
  • 节点执行线。 kubelet观察到分配给本节点的Pod,调用节点上的容器运行时准备沙箱、镜像、容器、网络和卷,并把执行结果与状态回报给API Server。

因此,“创建命令没有报错”只能证明请求在客户端侧获得了某种响应;它不能独立证明调度成功、镜像可以拉取、容器启动成功、探针通过或服务已经接收流量。排障时要先问清楚卡在哪一条线、哪个对象和哪个证据节点。

客户端请求先经过API Server的认证、授权和持久化

kubectl负责提交和观察,不负责直接启动容器

`kubectl apply`、`kubectl create`或其他客户端调用,通常会向Kubernetes API Server发起请求。客户端负责组装资源描述、发送请求、处理响应,也可以继续查询对象、事件和日志;它不是直接连接每个节点去执行容器的工具。

下面的YAML是一个用于流程验证的最小Pod示例。它没有指定具体镜像版本之外的生产基线,也不代表所有集群都允许该镜像或该安全上下文;正式使用前要按目标环境的镜像策略、命名空间和准入规则复核。

“`yaml

apiVersion: v1

kind: Pod

metadata:

name: pod-flow-check

namespace: demo

labels:

app: pod-flow-check

spec:

containers:

  • name: app

image: registry.example.invalid/demo/pod-flow-check:verify

ports:

  • containerPort: 8080

“`

验证方式:先将镜像地址替换为目标环境允许访问的测试镜像,并确认当前身份具有 `demo` 命名空间中的创建权限,再用客户端提交并查询对象。镜像地址仅为占位示例,不能直接执行;集群的准入策略、私有仓库凭据和安全限制可能使结果不同。

API Server处理请求,但不是所有请求都会落库

API Server是客户端、控制面组件和节点组件访问Kubernetes API的主要入口。请求进入后,通常要经过身份认证,判断调用者是谁;再经过授权,判断该身份是否可以在目标命名空间对Pod执行创建、读取或删除;之后还可能经过准入控制和对象校验,最后才把接受的对象持久化。

用职责表区分组件,排查会更清楚:

参与者 主要职责 不能据此推断的事情
kubectl / 客户端 提交、查询、删除和读取日志 / 事件等请求 不直接负责节点上的容器启动
API Server 认证、授权、准入、对象校验和API访问入口 返回接受不代表Pod已调度或容器已运行
持久化存储 保存被接受的集群对象及其状态数据 对象存在不代表节点执行成功
Scheduler 为符合条件的未绑定Pod选择节点并执行绑定动作 不负责在节点拉取镜像或启动容器
Controller 持续调谐管理对象的期望状态与实际状态 不等于每个Pod都由某个Controller直接创建
kubelet 在目标节点执行Pod并回报状态 不负责替代API Server做全局调度

API Server返回成功时,应继续查询对象状态和事件。若返回`Forbidden`,优先查RBAC和命名空间;若返回校验或准入错误,检查YAML、策略、资源和镜像引用;若对象已经存在但没有运行,则排查应转向调度和节点执行,而不是反复提交同一请求。

Scheduler负责绑定节点,Controller负责让期望状态持续存在

Scheduler解决“放到哪个节点”

新建的Pod如果没有可用的节点绑定信息,Scheduler会观察这类待调度对象,并根据资源请求、节点可用性、污点与容忍、节点选择、亲和性 / 反亲和性、拓扑等约束选择候选节点。不同版本、调度配置和扩展插件可能影响细节,本文只保留“从未绑定到绑定节点”的稳定协作关系,不展开具体过滤、打分顺序或默认插件行为。

调度成功后,Pod对象会带有节点归属或绑定结果。这个结果只说明控制面完成了放置决策,不代表节点上的镜像已经准备好。若Pod长时间处于Pending,应先查看调度事件和资源约束,而不是直接重启节点或删除Pod。

常见原因包括:

  • 资源请求超过当前可用资源,或命名空间配额、LimitRange限制了创建或调度
  • 节点选择、污点容忍、亲和性 / 反亲和性或拓扑约束没有匹配对象
  • 节点不可用、被隔离或不满足工作负载的标签条件
  • 准入、调度扩展或平台策略改变了对象能够使用的节点范围

Controller解决“期望状态是否被持续维持”

Controller不是一个单独负责“启动容器”的步骤,而是一组持续运行的调谐逻辑。以Deployment为例,Deployment期望某个版本和副本状态,相关控制器会通过ReplicaSet等对象组织Pod;如果直接创建一个裸Pod,则不应假设一定存在一个上层Controller替它重建。Job、DaemonSet、StatefulSet等管理对象也有各自的生命周期和调谐关系。

这一区分直接影响回滚和删除:删除Deployment管理的Pod,可能只是删除当前实例,Controller随后根据期望状态创建替代对象;删除裸Pod则不会因为某个上层工作负载对象而自动重建。执行删除前必须先识别Pod的管理者、命名空间、标签和业务影响,不能把删除当成通用回滚按钮。

kubelet把已绑定的Pod交给节点执行环境

当Pod已经绑定到某个节点,节点上的kubelet会观察到这个对象,并协调本节点的执行过程。它需要根据Pod描述准备容器运行环境,涉及容器运行时、镜像、网络、卷、资源和探针等节点侧条件。kubelet的职责是执行和汇报,不是跨集群为Pod重新选择节点。

可以将节点侧过程理解为几个相互关联的检查点:

1. kubelet确认Pod归属于本节点,并读取对象描述和相关配置引用。

2. 节点执行环境准备Pod所需的基础条件,包括网络、卷和容器沙箱等;具体步骤会受运行时和插件影响。

3. 容器运行时根据镜像和容器配置创建容器;如果镜像不可达、凭据无效、资源不足或运行时异常,容器可能停留在等待或创建失败状态。

4. kubelet把容器状态、Pod状态、重启次数和原因等信息回报到API Server,供客户端、控制器和观测系统查询。

5. 探针和应用进程状态继续改变Pod的可用性判断;容器进程存在,也不等于应用已经Ready或服务已经接收流量。

在节点侧排查时,事件通常比单个状态字段更接近“发生了什么”。镜像拉取失败要看镜像地址、凭据和节点网络;卷挂载失败要看声明、绑定和节点存储;容器反复退出要看日志、退出原因和应用配置。具体容器运行时的日志位置、字段和行为需按目标集群环境确认。

Pending、ContainerCreating、Running应该怎样区分

`Pending`通常表示Pod尚未完成运行准备,可能仍在等待调度、镜像、卷、网络或其他条件。它不是一个足够精细的根因结论。先通过事件判断是“没有合适节点”,还是已经绑定节点但执行准备失败。

`ContainerCreating`经常出现在容器等待创建的过程中,但它更像容器状态中的等待原因或展示信息,不应未经版本和字段核对就把它当作Pod phase的固定枚举。查询时要同时看Pod phase、容器状态、等待原因、事件和节点归属。

`Running`表示Pod中至少有满足相应条件的容器处于运行状态,但不能自动等同于业务可用。还要确认容器是否Ready、探针是否通过、端口和网络是否正确、日志是否持续报错,以及上层Service或其他流量入口是否已经找到该Pod。

下面的表格用于建立初步判断,不替代目标版本的字段定义和实际事件。

看到的现象 首先确认 常见排查方向
Pod长期Pending 是否已绑定节点,事件是否说明资源或约束问题 调度资源、配额、污点、亲和性、节点状态
已绑定但ContainerCreating 镜像、卷、网络和节点执行事件 镜像拉取、仓库凭据、挂载、运行时和插件
Running但未Ready 就绪探针、容器日志和端点状态 应用启动、配置依赖、探针、Service关联
Running且反复重启 容器退出原因、重启次数和上一次日志 应用错误、资源限制、探针、节点压力

验证状态时,下面的命令用于查询对象和事件。命令中的命名空间和Pod名称必须替换为测试环境真实值。第一条查看阶段、节点归属和容器状态摘要,第二条查看相关事件,第三条读取容器日志。

“`bash

kubectl get pod pod-flow-check -n demo -o wide

kubectl events -n demo –for pod/pod-flow-check

kubectl logs pod-flow-check -n demo -c app

“`

验证方式:先确认当前身份具有目标命名空间的 `get`、`list`、`watch` 和日志读取权限,再对照事件时间线判断卡点。不同kubectl版本可能对事件查询参数、输出字段或日志选项存在差异,正式排障手册应按目标版本实测;若命令不可用,应改用目标平台提供的事件与日志入口,而不是据此判定Pod机制异常。

事件和日志要按协作链验证

一次完整验证不应只截图`Running`。建议按照请求进入、对象保存、节点绑定、节点执行和状态回报的顺序保留证据:

1. 请求证据。 记录使用的命名空间、资源名称、客户端响应、操作者身份和变更时间,但不要保存token、Cookie或敏感凭据。

2. 对象证据。 查看Pod清单、状态、节点归属、容器状态和管理者引用,确认实际对象与提交内容是否一致。

3. 调度证据。 通过事件和对象字段确认为什么选择或没有选择某个节点,核对资源、标签、污点和拓扑约束。

4. 节点证据。 查看镜像、卷、网络、运行时和kubelet相关事件,定位ContainerCreating或启动失败的具体原因。

5. 应用证据。 查看容器日志、探针结果、重启次数和Service / 端点关联,确认“进程运行”是否已经转换为“应用可用”。

6. 恢复证据。 对受控故障或配置修复记录变更前后状态、事件、日志、回滚目标和业务影响,避免只保留最终正常截图。

如果企业使用Container Platform或其他平台化入口,平台侧可能将集群、项目、命名空间、配额、RBAC、工作负载、事件、日志、指标和故障排查入口集中呈现。这有助于让研发、运维和安全角色按权限查看同一条证据链,但平台入口仍需与底层Kubernetes对象和目标产品文档对照。不能因为平台显示了某个工作负载页面,就宣称完整支持所有Kubernetes API、字段或运行时行为。

权限、项目和命名空间会改变排查视野

Pod创建失败不一定是工作负载本身有问题,也可能是调用者没有在正确范围内执行动作。实际排查至少要核对用户或服务账号、目标项目、命名空间和角色绑定之间的关系。

常见权限边界包括:

  • 创建Pod的权限和读取Pod事件、日志的权限可能不属于同一个角色
  • 读取对象的权限不代表可以读取关联Secret或跨命名空间资源
  • 平台项目可能映射多个命名空间,但项目成员不必然拥有集群级权限
  • 调查节点级事件或kubelet日志通常需要更高权限,不能通过扩大普通开发者权限来“快速解决”
  • 删除Pod、Deployment或Job的权限影响面不同,审批和回滚对象也不同

Container Platform的知识边界可以承接项目、命名空间、配额、用户 / 组 / 角色、RBAC和审计线索,但这些入口不自动等同于企业完整权限治理、SSO兼容矩阵或合规结论。排障方案应遵循最小权限:先授予读对象、事件和日志所需的范围,只有明确需要时才申请变更或删除权限,并记录授权和撤销动作。

删除Pod不是回滚,恢复动作要看管理对象

删除操作会改变集群中的实际对象,不能作为无风险的“刷新页面”。删除前至少要确认:目标是否由Deployment、StatefulSet、DaemonSet、Job等管理;是否包含持久卷或重要临时数据;是否会触发重建、重新调度、重复处理或业务流量变化;谁批准以及如何恢复。

对于配置错误,更稳妥的处理通常是先保存当前对象、事件和日志证据,再修改源清单或管理对象,并通过受控变更观察新Pod。对于单个无状态实例的异常,删除可能触发上层Controller重建,但这并不等于问题已经修复;如果根因是镜像、配置、权限、资源或节点环境,新实例可能复现同一故障。

如果涉及Deployment版本回退,应回到Deployment及其发布记录层面核对目标版本,而不是只删除当前Pod。如果涉及Stateful工作负载、PVC、位点、队列或其他有状态数据,任何删除、重建和恢复都要让数据责任人参与。先保留证据、识别管理对象、明确影响面,再选择修复、暂停、回滚或删除。

用一条证据链完成创建流程验收

在测试或预发布命名空间中,可以用一个受控Pod完成以下验收:

  • 客户端身份能够在指定命名空间创建对象,授权边界符合最小权限
  • API Server返回后,对象能够被查询,清单、状态和时间线可以对应
  • Scheduler能够根据资源和约束完成节点绑定,失败时事件给出可行动线索
  • kubelet能够准备镜像、网络、卷和容器运行环境,节点侧异常可被定位
  • 容器状态能够从等待或创建阶段进入预期运行状态,日志可读取且无敏感信息泄露
  • `Running`之外还验证Ready、探针、重启、Service或其他流量入口的实际状态
  • 删除或修改前能识别管理者、数据对象、权限影响和恢复方式
  • 事件、日志、对象清单和变更记录可以按操作者、时间和对象串联

这类验收不是为了证明所有Kubernetes对象都已支持,而是验证目标环境中的一条工作负载创建链路。若平台项目还需要多集群、配额、审计、观测和故障排查,应把这些维度作为独立评估项,不从一个Pod的成功运行外推平台的完整能力。

下一步建议

先在受控项目和命名空间中创建一个最小Pod,记录客户端响应、对象清单、节点绑定、事件、容器日志、Ready状态和删除恢复结果。遇到异常时,按API Server、Scheduler、Controller、kubelet和应用五层排查,不要直接重复创建或删除来掩盖证据。

如果需要将这条流程纳入企业容器平台的日常入口,可继续沿容器与Kubernetes分类梳理工作负载、项目、命名空间、RBAC、观测和生产验收内容。Container Platform相关产品承接、完整API范围和平台页面URL应在正式评估前结合当前资料与目标环境核验。

常见问题

API Server返回创建成功,为什么Pod仍然没有Running?

API Server返回创建成功,通常只表示请求通过了当时的认证、授权、准入和对象校验,并且Pod对象已经被接受或写入持久化存储;它不表示Scheduler已经完成节点绑定,也不表示kubelet已经成功拉取镜像、准备网络与卷、创建容器并让应用通过就绪检查。排查时先用对象查询确认Pod是否存在、是否有节点归属,再查看事件判断是资源或调度约束、镜像拉取、挂载、网络还是运行时问题。若对象已经Running,还要继续确认Ready、探针和应用日志。权限不足读取事件或日志时,不应直接扩大集群管理员权限,而应申请目标命名空间内的最小读取权限,并保留操作者、时间和对象证据。

ContainerCreating是Pod phase吗?应该查什么?

不能把`ContainerCreating`未经核对就当作Pod phase的固定枚举。它常用于描述容器仍在等待创建或准备的状态,实际排查应同时查看Pod phase、容器的waiting reason、事件、节点归属和日志;不同版本、客户端输出和平台界面可能呈现不同字段。若Pod已绑定节点但长期停留在这个阶段,应优先查看镜像地址和仓库凭据、节点网络、卷挂载、容器运行时、资源限制以及相关插件事件。命令输出中的一行状态只能帮助定位方向,不能替代完整证据链。正式手册应在目标集群和kubectl版本中实测字段与查询方式,尤其要确认事件读取权限和平台对节点侧日志的展示范围。

Controller会不会直接创建容器?

Controller的主要作用是持续调谐管理对象的期望状态与实际状态,而不是绕过kubelet直接在节点上创建容器。以Deployment为例,控制器会围绕Deployment、ReplicaSet和Pod对象维持期望的副本与版本关系;真正把已绑定Pod交给节点执行、准备容器并回报状态的是kubelet及其节点执行环境。裸Pod、Job、DaemonSet和StatefulSet的管理关系也不同,不能把所有Pod都按同一重建逻辑理解。这个区分很重要:删除被Deployment管理的Pod,可能触发控制器创建替代实例;删除没有上层管理对象的裸Pod,则不会因为Controller期望副本而自动恢复。执行删除前应先检查owner references、标签、上层工作负载和数据影响。

删除一个Pod为什么有时会被重新创建?

因为它可能由Deployment、ReplicaSet、StatefulSet、DaemonSet或Job等上层管理对象维护,控制器发现实际副本或状态偏离期望值后,会尝试创建替代对象或推进任务状态。重新出现的Pod并不说明原故障已经消失:如果镜像、配置、权限、资源约束或节点环境没有变化,新实例仍可能进入Pending、ContainerCreating或反复重启。删除前要先确认Pod所属命名空间、owner references、标签、持久卷和业务影响,记录事件与日志,并明确删除是故障恢复、发布变更还是破坏性操作。若目标是回退版本,应修改并回退上层管理对象或发布版本;若目标是清理有状态数据、位点或任务结果,则必须让业务和数据责任人确认,不能把Pod删除当成通用回滚动作。

原创声明:本文为 Alauda 原创技术内容,非商业转载须注明出处:https://www.alauda.cn/blog/1602/。

文中图示和文章内容未经许可不得用于商业转载、培训课件、营销材料或二次分发。

(0)
Kafka中间件集群部署:生产级配置与运维最佳实践
上一篇 1天前
企业算力底座建设:单集群到跨地域算力互联的4阶段路线
下一篇 1天前

相关推荐