Kubernetes(K8s)的核心是控制平面(Control Plane),它负责维护集群的期望状态。在所有组件中,API Server 是集群唯一的入口。本篇文章将深入解析一个简单指令(例如创建或修改资源)从用户端(Client)发起,直至最终被持久化到 Etcd 的完整流转过程。
1. K8s 控制平面核心组件回顾
在追踪指令流之前,我们必须明确涉及的核心组件:
- Client (kubectl): 用户接口,用于发送 RESTful 请求。
- API Server: 集群的唯一前端,处理所有请求并验证它们。
- Etcd: 分布式键值存储,K8s 集群的单一真相来源(Source of Truth)。
- Controller Manager/Scheduler: 持续观察 Etcd 中的状态变化,驱动集群达到期望状态。
2. 指令流转的七个关键步骤
假设我们执行一个创建 Deployment 的命令:kubectl apply -f deployment.yaml。
步骤 1: Client 发起请求
kubectl 将用户的 YAML 文件转换为一个 HTTP API 调用(通常是 POST 或 PUT 请求),发送到配置的 API Server 地址。
# 示例操作:创建名为 'my-app' 的 Deployment
kubectl apply -f my-app.yaml
# 实际发生的网络请求(简化版):
# POST /apis/apps/v1/namespaces/default/deployments
# Host: k8s-api-server:6443
# Body: {... deployment object data ...}
步骤 2: API Server 接收请求
API Server 接收到请求后,立即开始处理请求头和路径。
步骤 3: 认证 (Authentication)
API Server 检查请求发起者的身份,例如通过客户端证书、Bearer Token 或 Service Account Token。如果身份未被识别,请求会被拒绝(HTTP 401 Unauthorized)。
步骤 4: 授权 (Authorization)
确定了请求者的身份后,API Server 检查该身份是否有权执行请求的操作(例如,用户 Alice 是否有权在 default 命名空间中创建 Deployment)。这通常通过 RBAC(Role-Based Access Control)策略来执行。如果无权限,请求会被拒绝(HTTP 403 Forbidden)。
步骤 5: 准入控制器 (Admission Controllers) – 关键的安全和策略检查点
这是指令流中最重要且最复杂的阶段。API Server 按照预设顺序执行一系列的准入控制器,它们分为两大类:
- 变动准入控制器 (Mutating Admission Controllers): 它们可以修改请求对象的内容。例如,给没有指定 Service Account 的 Pod 自动注入 default Service Account;或者注入 Sidecar 容器。
- 校验准入控制器 (Validating Admission Controllers): 它们无法修改请求,但会根据预设的集群策略或安全规则来检查请求的有效性。如果校验失败,请求将被拒绝。
实操提示:如果你使用了像 Gatekeeper 或 Kyverno 这样的策略引擎,它们通常以 Webhook 的形式实现自定义的 Validating Admission Controller。
步骤 6: 对象验证和持久化前处理
API Server 对请求对象进行最终的模式验证(Schema Validation),确保对象的结构和字段值符合 Kubernetes 规范。随后,API Server 会执行内部操作,例如设置资源版本(Resource Version)和生成内部 Etcd Key。
7: Etcd 持久化
这是指令流的终点。API Server 将经过所有安全检查、修改和验证的对象序列化(通常是 JSON 格式)后,使用其内部的 Etcd 客户端将对象作为键值对写入 Etcd 数据库。一旦数据成功写入 Etcd,K8s 集群的“期望状态”就更新完成了。
3. 后续状态流转(Controller Loop)
一旦对象写入 Etcd,指令流的直接部分结束。但 K8s 的魔力才刚刚开始:
- Controller Watch: Deployment Controller、Replication Controller 等通过 API Server 持续“Watch”Etcd 数据的变化。
- Reconciliation: 发现 Etcd 中的期望状态(Deployment/my-app 应该存在)与实际状态不符,Controller Manager 会采取行动,例如创建 ReplicaSet,进而让 Kubelet 在 Node 上启动 Pods,最终达到用户通过 kubectl 设定的目标状态。
汤不热吧