CodeRoad Map 程序员的学习成长路线图。内容免费开放,登录后可同步路线图与课时进度。
由 程序员柏风 独立维护 · 关于作者
学习 更多
核心概念与架构
这一课你将能做到
画出 K8s 架构:控制平面(API Server、etcd、Scheduler、Controller Manager)与工作节点(kubelet、kube-proxy)各自职责
说清核心对象关系链:Namespace → Deployment → ReplicaSet → Pod,以及 Service/Ingress 如何靠 Label 找到 Pod
解释 Label/Selector 的匹配规则,能预判「改标签」会引发什么后果
为什么要学
以后你敲的每一条 kubectl 命令,最终都打到一个叫 API Server 的组件上;集群的「真相」存在 etcd 里。不懂架构,遇到 Pending、CrashLoopBackOff、Service 后面没有 Endpoints 这类问题时只能瞎猜;懂了架构,你能立刻定位「这事归谁管、该看谁的日志」。
面试必考:「说说 K8s 架构」几乎是云原生方向的自我介绍题;「Deployment、ReplicaSet、Pod 什么关系」是第二高频。本课把这两题一次性打到能背的程度。
先建立图像
kubectl(你的终端) / CI 流水线
│
┌─────▼─────┐
│ API Server │ ←── 集群唯一入口:认证/鉴权/校验/存取
└─────┬─────┘
etcd(集群数据库:存所有对象的期望与实际状态)
│
┌───────────┴────────────┐
Scheduler Controller Manager
「新 Pod 放哪个节点」 「实际 ≠ 期望时自动修」(副本、节点、Job…)
│ 调度决定下发到节点
┌───────────▼───────────┐ ┌───────────────┐
│ Node 1 │ │ Node 2 │
│ kubelet ← 汇报状态、按单起容器、管探针 │
│ kube-proxy ← 维护 Service 转发规则(iptables/IPVS)│
│ 容器运行时(containerd) │
└────────────────────────┘ └───────────────┘
对象关系链(背下来):
Namespace(逻辑分区)
└─ Deployment(我要 3 个这样的 Pod)
└─ ReplicaSet(某一版本的副本集合)
└─ Pod(真正跑容器的地方,IP 随时可能变)
Service(稳定虚拟 IP + DNS,靠 label 选中一组 Pod)
Ingress(HTTP 路由,把外部流量按域名/路径分给 Service)
ConfigMap / Secret(配置与密钥,注入 Pod)
概念 一句话 本站对应 Pod 最小调度单元,1+ 容器共享网络 backend 的一个运行实例 Deployment 副本管理 + 滚动更新 backend 保持 3 副本 Service 稳定访问入口 platform 用 http://backend 调 API Label 对象的「名牌」,selector 靠它抓人 app=backendNamespace 集群内的逻辑隔离 业务放 coderoadmap,系统在 kube-system
跟着做
步骤 1:解剖一份 YAML 的固定骨架
所有 K8s 对象 YAML 都是同一副骨架(以 Pod 为例):
apiVersion: v1 # 属于哪个 API 组:核心对象 v1,工作负载 apps/v1
kind: Pod # 对象类型
metadata: # 名字、标签、注解、所属命名空间
name: hello
labels:
app: hello
spec: # 期望状态——你要它长什么样
containers:
- name: web
image: nginx:1.27-alpine
记住公式:apiVersion + kind 说「这是什么」,metadata 说「它叫什么、贴什么标签」,spec 说「它应该是什么样」。后面学 Deployment、Service、Ingress,全是这副骨架换字段。
步骤 2:命名空间清单(可保存复用) apiVersion: v1
kind: Namespace
metadata:
name: coderoadmap
集群装好后 kubectl apply -f namespace.yaml 即建好本站专属空间。直觉:default 放练手资源,kube-system 是系统组件(绝不能乱删),本站业务对象进 coderoadmap。
步骤 3:Label/Selector 绑定推演 + 验证命令 Service 靠 selector 抓 Pod:
# Pod 一侧
metadata:
labels:
app: backend
tier: api
# Service 一侧
spec:
selector:
app: backend # 只要求匹配这一项
推演:selector 是对 Pod 标签的子集匹配 ——Pod 可以有额外标签,但 selector 要求的每一个键值都必须存在。所以给 Pod 多加 tier=api 没影响;把 Pod 的 app 改掉,Service 立刻抓空。
kubectl get pods -l app=backend --show-labels
步骤 4:排错三板斧预习(集群可用后逐条跑) kubectl get pods # 有没有?状态是什么?
kubectl describe pod <pod名> # 发生了什么?看 Events 段
kubectl logs <pod名> # 应用自己说了什么?
口诀:get 看状态 → describe 看事件 → logs 看日志。九成入门问题靠这三条定位,顺序别反。
步骤 5:默写架构组件表再对照
API Server:唯一入口,所有读写经过它
etcd:键值数据库,存集群全部状态
Scheduler:决定新 Pod 放哪个节点
Controller Manager:跑各种控制器,负责调谐
kubelet:节点代理,管理本节点容器并汇报状态
kube-proxy:维护 Service 的网络转发规则
步骤 6:打印对象全貌(集群可用后) kubectl api-resources --namespaced=true
你会看到几十种对象。本 track 只需吃透:Pod、Deployment、ReplicaSet、Service、Ingress、ConfigMap、Secret、PVC、HPA——其余混个脸熟即可,面试也极少考冷门对象。
讲清楚要点
所有操作都过 API Server :kubectl、Dashboard、CI、甚至集群组件互相通信都走它,鉴权、审计、校验因此集中一处。「绕过 API 直接改 etcd」是严重事故行为。
etcd 是唯一真相源 :你 apply 的 YAML 与 Pod 实际状态都在里面。etcd 挂了整个集群变「只读僵尸」;生产要高可用,学习阶段不必操心。
控制器是 K8s 的灵魂 :每种资源背后都有控制器在死循环「对比期望/实际 → 修正」。删掉 Deployment 管的 Pod 会自动重建,就是 ReplicaSet 控制器发现少了。
调度单位是 Pod 不是容器 :同 Pod 容器共享网络命名空间(127.0.0.1 互访、共享端口空间)、可共享卷、同生共死。sidecar 模式(日志收集、代理)建立在这之上。
Label 是一切关联的粘合剂 :Service→Pod、Deployment→Pod、HPA→Deployment 全靠 selector。改标签等于改流量拓扑,发布与排错都要盯标签。
Namespace 是逻辑隔离不是硬边界 :它切分的是命名与配额,不是网络或权限的绝对屏障——真隔离要配 RBAC(第 11 课)与网络策略。
你可能会懵的地方
Master 和 Control Plane 什么关系?
同一个东西。旧文档叫 Master,现在统一叫「控制平面」。生产环境控制平面组件各跑多副本实现高可用;minikube 里它们全在一个节点上。
Pod IP 为什么不能写进配置文件?
Pod 每次重建 IP 都会变。应用之间必须通过 Service DNS 名互访(如 http://backend),这正是 Service 存在的理由——类比 Compose 里用服务名而不是容器 IP。
kube-proxy 就是一个 Nginx 反向代理吗?
不是。它是每个节点上维护转发规则(iptables/IPVS 模式)的组件,让「访问 Service 虚拟 IP」能被转发到真实 Pod。流量并不经过某个中心代理进程。
命令式命令(kubectl run / expose)能用吗?
学习冒烟可以,但它们不留痕迹、不可复现。工程实践:一切进 YAML 文件、进 Git,用 apply 管理——这就是「声明式」的工程价值。
ReplicaSet 为什么不直接用?
它只管「保持 N 个副本」,不管发布策略。Deployment 在它之上加了滚动更新与回滚。日常只操作 Deployment,让 RS 当隐身中间层。
错法对照 错法 问题 正解 只背对象名,不理解谁管谁 发布时乱删 ReplicaSet 酿事故 记住 Deployment→RS→Pod 管理链 Service 的 selector 与 Pod 标签对不上 Endpoints 为空,服务不通 get endpoints 核对标签所有资源堆在 default 且无标签规范 多服务后无法筛选排障 约定 app、tier 标签体系 把 Namespace 当安全边界 误以为不可能越权 Namespace + RBAC 双管齐下 遇到异常只看 STATUS 列 漏掉 Events 里的关键线索 必用 describe 看事件
卡点急救
apply 报 no matches for kind "Deployment" in version "v1" :apiVersion 写错。Deployment 是 apps/v1,Ingress 是 networking.k8s.io/v1,Pod/Service/ConfigMap 这类核心对象才是 v1。
报 namespaces "xxx" not found :YAML 里 metadata.namespace 指向不存在的命名空间,或忘了先 kubectl create namespace。
get 什么都没有,明明刚才创建了 :九成是 context 或 namespace 不对——kubectl config current-context、kubectl get pods -A 全局看一眼,别在错误空间里找。
面试常问
说说 Kubernetes 的架构?
控制平面:API Server(唯一入口,负责认证、鉴权、准入与读写)、etcd(存集群全部状态)、Scheduler(为 Pod 选节点)、Controller Manager(运行各控制器维持期望状态)。工作节点:kubelet(节点代理,管理容器生命周期并汇报状态)、kube-proxy(维护 Service 转发规则)、容器运行时。所有变更经 API Server 写入 etcd,控制器持续调谐实际状态。
Deployment、ReplicaSet、Pod 三者什么关系?
Deployment 是上层控制器,负责声明式发布:修改 Pod 模板会创建新 ReplicaSet,并按滚动策略让新旧 RS 副本数此消彼长;ReplicaSet 负责维持某个版本的固定副本数;Pod 是真正跑容器的单元。日常只操作 Deployment,不要直接动 RS。
Label 和 Annotation 的区别?
Label 是有筛选语义的键值对,被 selector 消费(Service 选 Pod、HPA 选 Deployment),要精简规范;Annotation 是无筛选语义的元数据,存描述性信息与工具配置,可放大量非结构化数据。一句话:Label 给机器筛选用,Annotation 给人和工具读。
自测三问
Scheduler 和 Controller Manager 分别负责什么?
为什么说「生产环境不要直接管理裸 Pod」?
本站 platform 和 backend 为什么是两个 Deployment,而不是塞进一个 Pod?
小结一句话 控制平面(API Server/etcd/Scheduler/Controller)存期望并调谐,节点上 kubelet/kube-proxy 落地容器与流量规则,Label 把 Service、Deployment 与 Pod 粘在一起——架构图和对象链装进脑子,下一课装本地集群动手。
延伸