考证匠/CKAD/第 1 章
第 1 章

核心概念

⏱️ 180 分钟📚 Application Design and Build难度: ⭐⭐
📝 15 题练习
备考助手

核心概念

📋 本章概览

主题考试权重重要程度
Pod 生命周期★★★★★必考
kubectl 操作★★★★★必考
Deployments★★★★★高频考点
ReplicaSets★★★★☆重要
命名空间★★★★☆重要
Labels/Selectors★★★★☆重要

💡 考试占比:Application Design and Build 占 CKAD 考试的 20%


🎯 学习目标

学完这一章,你应该能够:

  1. 从零理解 Pod 是什么 —— 为什么它是 Kubernetes 的最小部署单元
  2. 创建和管理 Pods、ReplicaSets 和 Deployments
  3. 熟练使用 kubectl 进行各种操作(考试 90% 的时间你都在敲 kubectl)
  4. 正确使用命名空间隔离资源
  5. Labels/Selectors 组织和筛选资源
  6. 掌握 Deployment 的滚动更新和回滚(实操高频考题)

📝 学习建议

通俗理解: 学 CKAD 核心概念,就像学开一家连锁餐厅

想象你要开一家连锁餐厅,每天要运营多个门店(容器化应用):

  • Pod(工位) —— 一个厨师的工作台。上面可能只有一套灶具(单容器),也可以有灶具 + 配菜台(多容器)。同一个工位上的设备共享水电和台面空间(共享网络和存储)
  • ReplicaSet(排班表) —— 确保"高峰期永远有 3 个厨师在岗"。一个厨师请假了?排班表自动叫替补来补位
  • Deployment(运营经理) —— 管理排班表,还负责"换菜单"。新菜单推出时,不是所有门店同时换(会导致停业),而是一家一家换(滚动更新)。换完发现新菜难吃?经理一键恢复旧菜单(回滚)
  • Namespace(不同城市的分部) —— 北京分部和上海分部各自独立运营,厨师名字可以重复。"dev 命名空间"和"prod 命名空间"各有各的资源,互不干扰
  • Labels(工牌标签) —— 每个厨师的工牌上贴着"岗位=主厨"、"区域=北京"。经理可以快速筛选"所有北京的主厨"
为什么第一章学核心概念?

CKAD 是纯实操考试——没有选择题,全程在终端敲命令。核心概念是你操作的基础对象,考试中几乎每道题都会用到 Pod、Deployment 和 kubectl。如果你不理解这些概念之间的关系,后面学 ConfigMap、Service、Ingress 都会很吃力。

本章知识地图:

CKAD 核心概念
│
├── Pod(最小部署单元)
│   ├── 容器共享网络 + 存储
│   ├── 生命周期:Pending → Running → Succeeded/Failed
│   └── 重启策略:Always / OnFailure / Never
│
├── kubectl(命令行工具 = 你的考试武器)
│   ├── 创建:run / create / apply
│   ├── 查看:get / describe / logs
│   ├── 修改:edit / set / label
│   ├── 删除:delete
│   └── 调试:exec / port-forward / explain
│
├── Deployment + ReplicaSet(应用管理)
│   ├── Deployment 管理 ReplicaSet,ReplicaSet 管理 Pod
│   ├── 滚动更新:kubectl set image
│   └── 回滚:kubectl rollout undo
│
├── Namespace(资源隔离)
│   └── 切换:kubectl config set-context --current --namespace=
│
└── Labels & Selectors(资源组织)
    ├── 打标签:kubectl label
    └── 筛选:kubectl get pods -l key=value

Kubernetes 整体架构

在深入具体概念之前,先看一眼 Kubernetes 集群的全局架构:

Kubernetes 集群组件

图解说明:

  1. 这张图在讲什么:一个 Kubernetes 集群由 Control Plane(控制平面)Worker Nodes(工作节点) 组成。Control Plane 负责"大脑决策"(调度、监控、API),Worker Node 负责"干活"(跑 Pod)。
  2. 你应该先看哪里:先看左侧 Control Plane 的 API Server —— 它是集群的"前台总机",所有请求(kubectl 命令、其他组件通信)都经过它。然后看右侧 Node 上的 kubelet 和容器运行时。
  3. 考试常见问法:CKAD 不直接考架构组件,但理解架构能帮你判断"为什么 Pod 调度失败"、"为什么 Service 不通"——这些排障题的根因往往和架构有关。

📖 Pod 到底是什么?

术语:Pod

  • 一句话解释:Kubernetes 里最小的部署单元。你不能直接部署一个容器,必须把它放进 Pod 里。
  • 形象比喻:Pod 像一个"工位"——上面可以放一套灶具(单容器),也可以放灶具 + 配菜台(多容器)。同一个工位上的设备共享水电(网络)和台面空间(存储卷)。
  • 考试怎么考:几乎每道题都涉及 Pod。最基础的考法是"创建一个满足特定要求的 Pod"。
  • 最易混淆:Pod ≠ 容器。一个 Pod 可以包含多个容器,它们共享 IP 地址和存储卷。

为什么不直接运行容器,而要包一层 Pod?因为 Kubernetes 需要一个统一的"调度单元"。Pod 提供了共享的网络命名空间(同一个 Pod 里的容器用 localhost 互相通信)和共享存储卷。这样紧密关联的容器(比如应用 + 日志收集器)可以放在同一个 Pod 里,像"坐同一辆班车"一样被调度到同一个节点。

Pod 架构

Pod 结构概览

图解说明:

  1. 这张图在讲什么:一个 Pod 内部的结构 —— 多个容器共享同一个网络命名空间(同一个 IP),并且可以挂载共享的 Volume。
  2. 你应该先看哪里:先看 Pod 的边界(外框),再看里面的容器和 Volume 之间的连线关系。注意容器之间通过 localhost 互通。
  3. 考试常见问法:考试会让你在 YAML 里定义多容器 Pod 并共享 Volume。理解这张图的关键是搞清楚"什么在 Pod 级别共享,什么在容器级别隔离"。
┌─────────────────────────────────────────────────────────┐
│                        Pod                               │
│  ┌─────────────────────────────────────────────────┐    │
│  │              共享网络命名空间                      │    │
│  │         (localhost 相互访问)                      │    │
│  └─────────────────────────────────────────────────┘    │
│                                                          │
│  ┌──────────────┐  ┌──────────────┐  ┌──────────────┐   │
│  │  Container 1 │  │  Container 2 │  │  Container N │   │
│  │   (nginx)    │  │   (sidecar)  │  │    (...)     │   │
│  │              │  │              │  │              │   │
│  │  Port: 80    │  │  Port: 9090  │  │              │   │
│  └──────────────┘  └──────────────┘  └──────────────┘   │
│         │                │                 │             │
│         └────────────────┼─────────────────┘             │
│                          │                               │
│  ┌─────────────────────────────────────────────────┐    │
│  │              共享存储卷 (Volumes)                 │    │
│  │     /data  ←──────────────────────→  /data       │    │
│  └─────────────────────────────────────────────────┘    │
│                                                          │
│  Pod IP: 10.244.1.5                                     │
│  Node: worker-node-1                                    │
└─────────────────────────────────────────────────────────┘

图解说明:

  1. 这张图在讲什么:一个 Pod 内部的结构——多个容器共享同一个网络和存储。
  2. 你应该先看哪里:先看"共享网络命名空间",这是 Pod 存在的核心原因。容器之间用 localhost 加端口号互访,不需要跨网络。
  3. 考试常见问法:给你一个多容器 Pod 场景,让你判断容器之间如何通信(答案:localhost),或让你配置共享 Volume。

创建 Pod

CKAD 是实操考试,速度就是分数。创建 Pod 有两种方式:命令式(快、适合考试)和声明式(完整、适合复杂配置)。

命令式方式(考试推荐,能省很多时间):

# 最简单的方式——一行搞定
kubectl run nginx --image=nginx

# 指定端口
kubectl run nginx --image=nginx --port=80

# 带环境变量
kubectl run nginx --image=nginx --env="DB_HOST=mysql"

# 带资源限制
kubectl run nginx --image=nginx --requests="cpu=100m,memory=256Mi"

# ⭐ 考试必用:生成 YAML 模板,然后再修改细节
kubectl run nginx --image=nginx --dry-run=client -o yaml > pod.yaml

💡 为什么推荐命令式? CKAD 考试一共 120 分钟,大约 15-20 道题。手写 YAML 太慢,用 --dry-run=client -o yaml 生成骨架再修改,能省一半时间。

声明式方式(需要复杂配置时用):

apiVersion: v1
kind: Pod
metadata:
  name: nginx
  labels:
    app: nginx
    env: production
spec:
  containers:
  - name: nginx
    image: nginx:1.21
    ports:
    - containerPort: 80
    resources:
      requests:
        memory: "64Mi"
        cpu: "250m"
      limits:
        memory: "128Mi"
        cpu: "500m"

resources 中的 requests 和 limits 有什么区别? requests 是"保底"——调度器保证节点至少有这么多资源给你;limits 是"天花板"——容器最多只能用这么多。超过 memory limits 会被 OOM Kill(直接杀掉),超过 cpu limits 会被限流(throttle,变慢但不杀)。

Pod 生命周期

Pod 从创建到结束会经历几个状态。理解这些状态是排查故障的基础——当 Pod 卡在某个状态时,你需要知道它卡在哪个阶段、可能是什么原因。

创建 Pod
    │
    ▼
┌─────────┐
│ Pending │ ← 等待调度或拉取镜像
└────┬────┘
     │
     ▼
┌─────────────────────────────────────────────────┐
│                   Running                        │
│  ┌─────────┐  ┌─────────┐  ┌─────────┐         │
│  │ Waiting │  │ Running │  │Terminated│         │
│  │(容器状态)│  │(容器状态)│  │(容器状态) │         │
│  └─────────┘  └─────────┘  └─────────┘         │
└───────────────────┬─────────────────────────────┘
                    │
        ┌───────────┼───────────┐
        ▼           ▼           ▼
  ┌──────────┐ ┌─────────┐ ┌─────────┐
  │Succeeded │ │ Failed  │ │ Unknown │
  │ (所有容器 │ │(至少一个 │ │(无法获取│
  │  成功退出)│ │ 失败退出)│ │  状态)  │
  └──────────┘ └─────────┘ └─────────┘

Pod 状态速查

状态描述常见原因一句话记忆
Pending已创建但未运行调度中、拉取镜像"在排队等位"
Running至少一个容器运行正常状态"已上岗干活"
Succeeded所有容器成功终止Job 完成"活干完了,下班"
Failed至少一个容器失败应用错误、OOM"出了事故"
Unknown无法获取状态节点通信问题"失联了"

容器状态

Pod 是 Running 不代表里面每个容器都正常。Pod 状态和容器状态是两层概念:

容器状态描述一句话记忆
Waiting等待启动(拉取镜像、等待依赖)"还没准备好"
Running容器正在运行"在干活"
Terminated容器已终止(成功或失败)"已退出"

⚠️ 考试视角kubectl describe pod 会显示每个容器的具体状态和原因(Reason),这是排查问题的第一步。

重启策略

当容器崩溃时,Kubernetes 会根据重启策略决定是否拉起来。选错重启策略是常见的考试失分点。

spec:
  restartPolicy: Always  # 默认,适合长期运行服务
  # restartPolicy: OnFailure  # 失败时重启,适合 Job
  # restartPolicy: Never      # 不重启,适合一次性任务
策略描述使用场景一句话记忆
Always总是重启Deployment、DaemonSet"永不放弃"
OnFailure失败时才重启Job"失败了再来一次"
Never不重启调试、一次性脚本"做完拉倒"

💡 常见陷阱:考试让你创建 Job 时,如果你忘记设 restartPolicy: OnFailure(或 Never),Job 的 Pod 会一直重启,永远不会变成 Completed 状态。


🔧 kubectl:你的考试武器

术语:kubectl

  • 一句话解释:Kubernetes 的命令行工具,你通过它跟集群"对话"——创建资源、查看状态、排查问题。
  • 形象比喻:kubectl 就像"遥控器"。你不需要走进机房(API Server),拿着遥控器就能操作一切。
  • 考试怎么考:CKAD 全程在终端操作,kubectl 是你唯一的工具。打字速度和命令熟练度直接决定分数。
  • 最易混淆:kubectl apply vs kubectl create。create 只能创建新资源,apply 可以创建也可以更新。考试中推荐统一用 apply。

创建资源

# 从 YAML 创建(声明式,推荐)
kubectl apply -f pod.yaml

# 快速创建 Pod(命令式,考试快)
kubectl run nginx --image=nginx

# 快速创建 Deployment
kubectl create deployment nginx --image=nginx --replicas=3

# ⭐ 考试必备:生成 YAML 模板,不实际创建
kubectl run nginx --image=nginx --dry-run=client -o yaml
kubectl create deployment nginx --image=nginx --dry-run=client -o yaml

--dry-run=client -o yaml 是什么意思? --dry-run=client 让 kubectl 只"假装"创建,不真的发请求给集群;-o yaml 把结果输出为 YAML 格式。两个组合起来 = "帮我生成 YAML 模板"。考试中你几乎每道题都会用到这个组合。

查看资源

排查问题的第一步,永远是"看看现在什么情况"。

# 列出 Pods(最常用)
kubectl get pods
kubectl get pods -o wide           # 显示更多信息(IP、节点)
kubectl get pods -o yaml           # YAML 格式输出
kubectl get pods --show-labels     # 显示标签
kubectl get pods -l app=nginx      # 按标签筛选
kubectl get pods -A                # 所有命名空间
kubectl get pods -n kube-system    # 指定命名空间

# 查看 Pod 详细信息和事件(排查故障的核心命令)
kubectl describe pod nginx

# 查看日志(应用报错时第一时间看日志)
kubectl logs nginx                  # 当前日志
kubectl logs nginx -f               # 实时跟踪(像 tail -f)
kubectl logs nginx --tail=100       # 最后 100 行
kubectl logs nginx -c sidecar       # 多容器 Pod 指定容器
kubectl logs nginx --previous       # ⭐ 上次崩溃的日志(排查 CrashLoopBackOff 必用)

# 查看资源使用
kubectl top pods
kubectl top nodes

⚠️ 考试视角kubectl describekubectl logs --previous 是排查三大金刚中的两个。第三个是 kubectl get events。碰到 Pod 不正常,按这个顺序排查:describe → logs → events。

修改资源

# 编辑资源(打开编辑器直接改)
kubectl edit pod nginx

# 更新镜像
kubectl set image pod/nginx nginx=nginx:1.22

# 打标签
kubectl label pod nginx env=prod
kubectl label pod nginx env=staging --overwrite  # 覆盖已有标签
kubectl label pod nginx env-                      # 删除标签

# 添加注解(annotation,和 label 不同,不参与筛选)
kubectl annotate pod nginx description="My pod"

# 替换资源
kubectl replace -f pod.yaml
kubectl replace -f pod.yaml --force  # 强制替换(删除重建)

删除资源

# 删除 Pod
kubectl delete pod nginx

# 从文件删除
kubectl delete -f pod.yaml

# ⭐ 强制删除(跳过优雅终止期,考试省时间)
kubectl delete pod nginx --force --grace-period=0

# 删除所有 Pods
kubectl delete pods --all
kubectl delete pods --all -n dev

# 按标签删除
kubectl delete pods -l app=nginx

💡 为什么考试要用 --force --grace-period=0 正常删除一个 Pod 需要等待 30 秒的优雅终止期(graceful shutdown)。考试中每秒都珍贵,加上这个参数可以立即删除,省下等待时间。

进入容器和端口转发

调试应用问题时,经常需要"钻进"容器里看看:

# 进入容器(交互式 shell)
kubectl exec -it nginx -- /bin/bash
kubectl exec -it nginx -- /bin/sh   # 容器里没 bash 时用 sh

# 执行单个命令(不进入交互)
kubectl exec nginx -- ls /etc
kubectl exec nginx -- cat /etc/nginx/nginx.conf
kubectl exec nginx -- env

# 多容器 Pod 指定容器
kubectl exec -it nginx -c sidecar -- /bin/sh

# 端口转发(本地测试 Pod 服务)
kubectl port-forward nginx 8080:80
kubectl port-forward svc/nginx-service 8080:80

exec -it 中的 -i-t 是什么意思? -i = interactive(保持标准输入打开),-t = tty(分配一个终端)。两个合在一起,你才能像 SSH 一样在容器里敲命令。如果只执行一条命令(如 ls),不需要 -it


📖 Deployment:应用的"运营经理"

术语:Deployment

  • 一句话解释:管理无状态应用的控制器。你告诉它"我要 3 个 nginx 副本",它负责创建、维护、更新这 3 个副本。
  • 形象比喻:Deployment 就是连锁餐厅的"运营经理"。经理确保每家门店(Pod)都在营业,有门店关了就开新的补上;要换菜单(更新镜像)时,一家一家换,保证不停业。
  • 考试怎么考:创建 Deployment、更新镜像(滚动更新)、回滚到之前版本——这三个操作是高频考题。
  • 最易混淆:Deployment vs ReplicaSet。你几乎永远不需要直接操作 ReplicaSet,Deployment 会帮你管理它。

Deployment、ReplicaSet、Pod 的关系

Deployment 管理流程

图解说明:

  1. 这张图在讲什么:kubectl 如何通过 Deployment 将容器化应用部署到 Kubernetes 集群中。Deployment 指示 Kubernetes 创建和更新应用实例。
  2. 你应该先看哪里:先看用户的 kubectl 命令如何到达 API Server,再看 Deployment 如何在 Node 上创建 Pod。
  3. 考试常见问法:kubectl create deploymentkubectl apply -f 是创建 Deployment 的两种方式。考试通常要求你用命令行快速创建,然后用 kubectl get deploy,rs,pods 验证三者关系。

很多初学者搞不清这三者的关系。简单来说:Deployment 管 ReplicaSet,ReplicaSet 管 Pod。就像公司组织架构——总监(Deployment)管经理(ReplicaSet),经理管员工(Pod)。

ReplicaSet(副本集) — 确保"指定数量的 Pod 副本始终在运行"。如果一个 Pod 挂了,ReplicaSet 会自动创建新的补上。你不用直接创建 ReplicaSet,Deployment 在背后会帮你创建和管理它。

┌─────────────────────────────────────────────────────────┐
│                     Deployment                           │
│                    (nginx-deploy)                        │
│                                                          │
│   replicas: 3                                           │
│   strategy: RollingUpdate                               │
│                                                          │
│   ┌─────────────────────────────────────────────────┐   │
│   │                  ReplicaSet                      │   │
│   │              (nginx-deploy-7d6f...)              │   │
│   │                                                  │   │
│   │  ┌─────────┐  ┌─────────┐  ┌─────────┐         │   │
│   │  │  Pod 1  │  │  Pod 2  │  │  Pod 3  │         │   │
│   │  │ nginx   │  │ nginx   │  │ nginx   │         │   │
│   │  │ :1.21   │  │ :1.21   │  │ :1.21   │         │   │
│   │  └─────────┘  └─────────┘  └─────────┘         │   │
│   │                                                  │   │
│   └─────────────────────────────────────────────────┘   │
└─────────────────────────────────────────────────────────┘

图解说明:

  1. 这张图在讲什么:Deployment → ReplicaSet → Pod 的三层管理结构。
  2. 你应该先看哪里:先看 replicas: 3,这决定了 ReplicaSet 要维持 3 个 Pod 副本。
  3. 考试常见问法:让你"扩容到 5 个副本"或"更新镜像后查看滚动状态"。理解这个层级关系,你就知道为什么 kubectl get rs 能看到新旧两个 ReplicaSet。

创建 Deployment

命令式(考试快速出活):

# 创建 Deployment
kubectl create deployment nginx --image=nginx

# 指定副本数
kubectl create deployment nginx --image=nginx --replicas=3

# 指定端口
kubectl create deployment nginx --image=nginx --port=80

# 生成 YAML 模板
kubectl create deployment nginx --image=nginx --replicas=3 --dry-run=client -o yaml > dep.yaml

声明式(完整配置):

apiVersion: apps/v1
kind: Deployment
metadata:
  name: nginx-deployment
  labels:
    app: nginx
spec:
  replicas: 3
  selector:
    matchLabels:
      app: nginx
  template:
    metadata:
      labels:
        app: nginx
    spec:
      containers:
      - name: nginx
        image: nginx:1.21
        ports:
        - containerPort: 80
        resources:
          requests:
            cpu: 100m
            memory: 128Mi
          limits:
            cpu: 200m
            memory: 256Mi

⚠️ 关键注意selector.matchLabelstemplate.metadata.labels 必须匹配。这是很多人写 YAML 时犯的错——两边标签不一致,Deployment 就无法管理 Pod,直接报错。

管理 Deployment

# 扩缩容(考试常考)
kubectl scale deployment nginx --replicas=5

# 自动扩缩容(根据 CPU 使用率)
kubectl autoscale deployment nginx --min=2 --max=10 --cpu-percent=80

# 查看状态
kubectl get deployment nginx
kubectl describe deployment nginx

# 查看 ReplicaSet(更新时会看到新旧两个 RS)
kubectl get rs

Deployment 扩缩容

图解说明:

  1. 这张图在讲什么:Deployment 通过调整 replicas 数量实现应用的水平扩缩容。扩容时新增 Pod 被调度到集群中的不同节点,缩容时多余的 Pod 被终止。
  2. 你应该先看哪里:先看 Service 如何将流量分发到多个 Pod,再看 Pod 数量的变化(从少到多)。注意每个 Node 上可以运行多个 Pod。
  3. 考试常见问法:kubectl scale deployment/NAME --replicas=N 是手动扩缩容。kubectl autoscale 是 HPA 自动扩缩容。考试常让你把副本数从 3 调到 5,或者根据场景选择合适的副本数。

滚动更新——如何"不停业换菜单"

滚动更新是 Deployment 最重要的功能。它的原理是:创建一个新的 ReplicaSet,逐步把 Pod 从旧 RS 迁到新 RS,直到所有 Pod 都跑新版本。这个过程中,始终有 Pod 在服务,用户不会感知到中断。

滚动更新过程

图解说明:

  1. 这张图在讲什么:Deployment 滚动更新的过程 —— 新版 Pod 逐个替换旧版 Pod,Service 始终将流量导向可用的 Pod,用户感知不到中断。
  2. 你应该先看哪里:先看新旧两组 Pod 的数量变化(旧的减少,新的增加),再看 Service 如何动态切换指向。
  3. 考试常见问法:kubectl set image deployment/NAME CONTAINER=IMAGE 触发更新,kubectl rollout status 查看进度,kubectl rollout undo 回滚 —— 这三条命令是滚动更新的核心操作。
# ⭐ 更新镜像(考试高频)
kubectl set image deployment/nginx nginx=nginx:1.22

# 更新资源限制
kubectl set resources deployment/nginx -c nginx --limits=cpu=200m,memory=512Mi

# 查看滚动进度
kubectl rollout status deployment/nginx

# 暂停滚动(需要分阶段发布时)
kubectl rollout pause deployment/nginx

# 恢复滚动
kubectl rollout resume deployment/nginx

回滚——"新菜单翻车了"

更新出问题时,回滚让你快速恢复到之前的版本。Deployment 会保留历史 ReplicaSet,所以回滚本质上就是"重新激活旧的 ReplicaSet"。

# 查看历史版本
kubectl rollout history deployment/nginx

# 查看特定版本的详情
kubectl rollout history deployment/nginx --revision=2

# ⭐ 回滚到上一版本
kubectl rollout undo deployment/nginx

# 回滚到指定版本
kubectl rollout undo deployment/nginx --to-revision=1

💡 考试典型题:创建 Deployment → 更新镜像 → 查看滚动状态 → 回滚。这四步串起来就是一道完整的考题,务必练到肌肉记忆。

更新策略

Deployment 支持两种更新策略,选哪个取决于你的应用是否允许"新旧版本同时存在":

spec:
  strategy:
    type: RollingUpdate  # 或 Recreate
    rollingUpdate:
      maxSurge: 25%        # 更新时最多可以多出多少 Pod
      maxUnavailable: 25%  # 更新时最多可以少多少 Pod
策略描述使用场景一句话记忆
RollingUpdate逐步替换(默认)零停机更新"边拆边建,不停业"
Recreate先全删,再全建不允许多版本共存(如数据库迁移)"先关门装修,再开门"

maxSurge 和 maxUnavailable 怎么理解? 假设 replicas=4,两者都是 25%:更新时最多同时有 5 个 Pod(4 + 1 surge),最少有 3 个 Pod 在服务(4 - 1 unavailable)。考试中一般不会改这两个参数,但要理解它们的含义。


🏷️ 命名空间:资源的"隔离间"

Node 与 Pod 的关系

图解说明:

  1. 这张图在讲什么:Kubernetes 集群中 Node 和 Pod 的关系 —— 每个 Node 上运行着 kubelet(负责管理 Pod)和容器运行时(负责运行容器)。Node 是实际的工作机器,Pod 被调度到 Node 上执行。
  2. 你应该先看哪里:先看 Node 这个边界框,它代表一台机器(物理机或虚拟机)。再看 Node 内部的 Pod 和系统组件(kubelet、kube-proxy)。
  3. 考试常见问法:理解 Node-Pod 关系能帮你排障。比如 Pod 状态 Pending 可能是因为没有可用 Node(资源不足),Pod 状态 ImagePullBackOff 可能是 Node 上拉不到镜像。

术语:Namespace(命名空间)

  • 一句话解释:把集群资源分组隔离的机制。不同命名空间里可以有同名资源,互不干扰。
  • 形象比喻:命名空间就像"楼层"。同一栋大楼里,3 楼的 101 室和 5 楼的 101 室是两个不同的房间。你在 dev 命名空间和 prod 命名空间各创建一个叫 nginx 的 Pod,它们互不影响。
  • 考试怎么考:考题会指定在某个命名空间操作。忘记加 -n 参数是最常见的丢分原因之一。
  • 最易混淆:命名空间隔离的是"资源名称",不是网络。不同命名空间的 Pod 默认可以互相通信(除非设了 NetworkPolicy)。

基本操作

# 查看命名空间
kubectl get namespaces
kubectl get ns    # 简写

# 创建命名空间
kubectl create namespace dev
kubectl create ns staging

# 在指定命名空间中创建资源
kubectl run nginx --image=nginx -n dev

# 查看指定命名空间的资源
kubectl get pods -n dev
kubectl get all -n dev

# 查看所有命名空间的资源
kubectl get pods -A
kubectl get pods --all-namespaces

# ⭐ 设置默认命名空间(考试强烈推荐!)
kubectl config set-context --current --namespace=dev

# 删除命名空间(会连带删除里面所有资源!)
kubectl delete namespace dev

⚠️ 考试生存技巧:每道题开头通常会指定命名空间。做题第一件事就是切换默认命名空间kubectl config set-context --current --namespace=xxx。这样后续所有命令都不用加 -n,既省时间又不容易忘记。

命名空间 YAML

apiVersion: v1
kind: Namespace
metadata:
  name: dev
  labels:
    env: development

集群默认命名空间

Kubernetes 集群自带 4 个命名空间,不要去动它们(除了 default):

命名空间用途一句话记忆
default默认命名空间,不指定 -n 就在这里"你的默认工位"
kube-system系统组件(API Server、etcd、kube-proxy 等)"机房,别乱动"
kube-public公开可读的资源"公告栏"
kube-node-lease节点心跳信息"签到表"

🏷️ Labels 和 Selectors:资源的"标签系统"

术语:Label(标签)

  • 一句话解释:贴在 Kubernetes 资源上的键值对标记,用于组织和筛选资源。
  • 形象比喻:就像超市货架上的分类标签——"水果/进口/打折"。你可以快速找到"所有打折的进口水果"。
  • 考试怎么考:Service 通过 selector 匹配 Pod 的 label 来做流量转发;Deployment 通过 selector 管理 Pod。标签不匹配 = 资源关联断开。
  • 最易混淆:Label vs Annotation。Label 参与筛选(selector 能选到),Annotation 只是"备注"(纯记录信息,不能被 selector 选到)。

添加和管理 Labels

# 添加标签
kubectl label pod nginx env=prod tier=frontend

# 覆盖已有标签
kubectl label pod nginx env=staging --overwrite

# 删除标签(注意减号语法)
kubectl label pod nginx env-

# 查看标签
kubectl get pods --show-labels

# 按标签筛选(selector 语法)
kubectl get pods -l env=prod                    # 等于
kubectl get pods -l 'env in (prod, staging)'    # 包含
kubectl get pods -l 'env!=dev'                  # 不等于
kubectl get pods -l env=prod,tier=frontend      # 多条件 AND

⚠️ 考试视角:Label selector 是 Kubernetes 里"关联资源"的核心机制。Service 找 Pod、Deployment 管 Pod、NetworkPolicy 选 Pod,全靠 label 匹配。写 YAML 时 selector 和 template labels 不一致,是最常见的"为什么我的 Service 没有流量"问题。

Labels 最佳实践

Kubernetes 官方推荐使用带前缀的标签:

metadata:
  labels:
    # 官方推荐的标签(带 app.kubernetes.io/ 前缀)
    app.kubernetes.io/name: nginx
    app.kubernetes.io/version: "1.21"
    app.kubernetes.io/component: frontend
    app.kubernetes.io/part-of: my-app
    app.kubernetes.io/managed-by: kubectl

    # 自定义标签(考试常用)
    env: production
    team: backend
    cost-center: engineering

考试中不会考官方标签规范,但你自己打标签时用 app=xxx, env=xxx, tier=xxx 这种清晰的键值对就好。


🎯 考试技巧

开考前必做的环境设置

# 1. 确认别名可用(考试环境通常已配置)
alias k=kubectl

# 2. 设置快捷变量 ⭐ 这两个能救命
export do="--dry-run=client -o yaml"
export now="--force --grace-period=0"

# 3. 使用示例
k run nginx --image=nginx $do > pod.yaml    # 生成 YAML
k delete pod nginx $now                      # 秒删 Pod

# 4. 查看字段文档(忘了 YAML 怎么写时用)
k explain pod.spec.containers
k explain pod.spec.containers.resources
k explain deployment.spec.strategy

# 5. 快速切换命名空间(每道题第一步)
k config set-context --current --namespace=dev

快速创建各种资源

考试中你需要快速创建不同类型的资源,把这些命令练到肌肉记忆:

# Pod
k run nginx --image=nginx $do

# Deployment
k create deployment nginx --image=nginx --replicas=3 $do

# 暴露为 Service
k expose deployment nginx --port=80 --type=NodePort $do

# Job
k create job test --image=busybox -- echo "hello" $do

# CronJob
k create cronjob test --image=busybox --schedule="*/5 * * * *" -- date $do

常用 kubectl 组合技

# 查看 Pod 所在节点
k get pods -o wide

# 提取 Pod IP(jsonpath 是考试利器)
k get pod nginx -o jsonpath='{.status.podIP}'

# 查看所有资源
k get all

# 服务端验证 YAML 是否正确(比 client 更严格)
k apply -f pod.yaml --dry-run=server

# 实时观察资源变化
k get pods -w

⚠️ 常见错误与排查

CKAD 考试大量考排查能力。以下是最常见的 5 种 Pod 故障,遇到任何一个都按"describe → logs → events"的顺序排查。

错误 1:Pod 一直 Pending——"卡在排队"

Pod 停在 Pending 意味着调度器找不到合适的节点来运行它。

# 看到这个状态
kubectl get pods
# NAME    READY   STATUS    RESTARTS   AGE
# nginx   0/1     Pending   0          5m

# 第一步:看 Events 找原因
kubectl describe pod nginx
常见原因Events 关键词解决方案
资源不足Insufficient cpu/memory降低 requests 或扩容节点
节点选择器不匹配0/3 nodes are available检查 nodeSelector / nodeAffinity
PVC 未绑定persistentvolumeclaim not found创建对应的 PV 或修复 PVC
污点/容忍had taints that pod didn't tolerate加 tolerations 或去掉节点 taint

错误 2:ImagePullBackOff——"找不到菜谱"

镜像拉不下来,通常是名字写错了。

kubectl get pods
# NAME    READY   STATUS             RESTARTS   AGE
# nginx   0/1     ImagePullBackOff   0          5m

# 排查
kubectl describe pod nginx | grep -A5 "Events"
常见原因解决方案
镜像名拼写错误kubectl set image pod/nginx nginx=nginx:1.21
镜像 tag 不存在去 Docker Hub 确认 tag
私有仓库认证失败检查 imagePullSecrets
网络问题检查节点网络连通性

💡 快速修复:如果只是镜像名写错,可以直接 kubectl edit pod nginx 修改镜像,不用重建。

错误 3:CrashLoopBackOff——"反复翻车"

容器启动后立刻崩溃,Kubernetes 反复尝试重启,间隔越来越长(10s → 20s → 40s...)。

kubectl get pods
# NAME    READY   STATUS             RESTARTS   AGE
# app     0/1     CrashLoopBackOff   5          10m

# ⭐ 关键命令:看上次崩溃前的日志
kubectl logs app --previous
kubectl describe pod app
常见原因排查方式
应用配置错误logs --previous 看错误信息
缺少环境变量describe 检查 env
健康检查太严格检查 liveness probe 配置
内存限制太小describe 看 OOMKilled

错误 4:Selector 不匹配——"标签对不上"

这个错误不会显示为 Pod 状态异常,而是表现为"Deployment 创建了但没有 Pod"或"Service 没有流量"。

# ❌ 错误:selector 和 template labels 不匹配
apiVersion: apps/v1
kind: Deployment
metadata:
  name: nginx
spec:
  selector:
    matchLabels:
      app: nginx      # selector 要找 app=nginx
  template:
    metadata:
      labels:
        app: web      # ← 但 Pod 标签是 app=web,对不上!

# ✅ 正确:selector 和 template labels 必须一致
spec:
  selector:
    matchLabels:
      app: nginx
  template:
    metadata:
      labels:
        app: nginx    # ← 和 selector 一致 ✓

错误 5:忘记指定命名空间——"走错楼层"

这是考试中最冤枉的丢分方式——操作正确,但在错误的命名空间执行。

# ❌ 忘记切换命名空间
kubectl get pods               # 在 default 命名空间,看不到 dev 里的资源
# No resources found

# ✅ 正确做法
kubectl get pods -n dev        # 方式 1:手动指定
kubectl config set-context --current --namespace=dev  # 方式 2:切换默认(推荐)

⚠️ 考试铁律:每道题做第一件事就是切换到题目指定的命名空间。把这个变成条件反射。


📝 考试场景题

场景 1:创建带资源限制的 Pod

题目:创建一个名为 resource-pod 的 Pod,使用 nginx 镜像,设置 CPU 请求为 100m,内存请求为 128Mi,CPU 限制为 200m,内存限制为 256Mi。

解题思路:先用 --dry-run 生成骨架,再添加 resources 字段。

# 第 1 步:生成 YAML 骨架
kubectl run resource-pod --image=nginx --dry-run=client -o yaml > pod.yaml

# 第 2 步:编辑添加 resources(用 vim)
apiVersion: v1
kind: Pod
metadata:
  name: resource-pod
spec:
  containers:
  - name: nginx
    image: nginx
    resources:
      requests:
        cpu: "100m"
        memory: "128Mi"
      limits:
        cpu: "200m"
        memory: "256Mi"
# 第 3 步:应用并验证
kubectl apply -f pod.yaml
kubectl describe pod resource-pod | grep -A10 "Limits"

💡 不确定 resources 字段怎么写?kubectl explain pod.spec.containers.resources 查看官方文档,考试中可以随时用。

场景 2:Deployment 滚动更新和回滚

题目:创建 Deployment,更新镜像版本,然后回滚。

解题思路:这是一个典型的四步操作——创建 → 更新 → 观察 → 回滚。

# 1. 创建 Deployment
kubectl create deployment web --image=nginx:1.19 --replicas=3

# 2. 验证 Pod 就绪
kubectl get deployment web
kubectl get pods -l app=web

# 3. 更新镜像
kubectl set image deployment/web nginx=nginx:1.21

# 4. 查看滚动状态(确认更新成功)
kubectl rollout status deployment/web

# 5. 查看历史版本
kubectl rollout history deployment/web

# 6. 假设新版本有问题,回滚到上一版本
kubectl rollout undo deployment/web

# 7. 验证回滚成功
kubectl describe deployment web | grep Image

场景 3:多命名空间资源管理

题目:在 production 命名空间创建 Pod,然后列出所有命名空间的 Pod。

# 1. 创建命名空间
kubectl create namespace production

# 2. 切换到该命名空间(养成好习惯)
kubectl config set-context --current --namespace=production

# 3. 创建 Pod(因为已切换命名空间,不用加 -n)
kubectl run prod-nginx --image=nginx

# 4. 验证
kubectl get pods

# 5. 列出所有命名空间的 Pod
kubectl get pods -A

场景 4:使用标签筛选和管理资源

题目:给 Pod 添加标签,然后按标签筛选和删除。

# 1. 创建多个 Pod
kubectl run app1 --image=nginx
kubectl run app2 --image=nginx
kubectl run app3 --image=nginx

# 2. 添加标签
kubectl label pod app1 env=prod tier=frontend
kubectl label pod app2 env=prod tier=backend
kubectl label pod app3 env=dev tier=frontend

# 3. 按标签筛选
kubectl get pods -l env=prod                    # 所有 prod 环境
kubectl get pods -l tier=frontend               # 所有 frontend
kubectl get pods -l env=prod,tier=frontend      # prod 且 frontend(只有 app1)
kubectl get pods --show-labels                  # 查看所有标签

# 4. 按标签批量删除
kubectl delete pods -l env=dev                  # 只删 dev 环境的

练习题

题目 1

创建一个名为 redis 的 Pod,使用 redis:alpine 镜像:

<details> <summary>查看答案</summary>
kubectl run redis --image=redis:alpine

验证:

kubectl get pod redis
kubectl describe pod redis
</details>

题目 2

将 Deployment nginx 的副本数从 3 扩展到 5:

<details> <summary>查看答案</summary>
kubectl scale deployment nginx --replicas=5

验证:

kubectl get deployment nginx
kubectl get pods -l app=nginx
</details>

题目 3

如何查看 Pod 上次崩溃前的日志?

  • A. kubectl logs pod-name
  • B. kubectl logs pod-name --previous
  • C. kubectl logs pod-name --last
  • D. kubectl describe pod pod-name
<details> <summary>查看答案</summary>

答案:B

解析

  • --previous 参数用于查看上一个已终止容器的日志
  • 这是排查 CrashLoopBackOff 的核心命令——容器已经崩溃重启了,当前日志可能是空的或不完整的,你需要看"上一轮"的日志
  • kubectl logs pod-name 只查看当前运行中容器的日志
kubectl logs pod-name --previous
</details>

题目 4

哪个命令可以生成 Pod YAML 而不实际创建?

  • A. kubectl run nginx --image=nginx --dry-run
  • B. kubectl run nginx --image=nginx --dry-run=client -o yaml
  • C. kubectl run nginx --image=nginx --output=yaml
  • D. kubectl create pod nginx --image=nginx --dry-run
<details> <summary>查看答案</summary>

答案:B

解析

  • --dry-run=client 表示客户端模拟,不发送请求到 API Server
  • -o yaml 指定输出格式为 YAML
  • 注意选项 A 缺少 =client(旧版本不带参数的 --dry-run 已废弃)
  • 选项 D 语法错误,kubectl create 后面不能直接跟 pod,应该用 kubectl run
kubectl run nginx --image=nginx --dry-run=client -o yaml > pod.yaml
</details>

题目 5(实操题)

创建一个 Deployment 名为 web-app,使用镜像 nginx:1.19,副本数为 3,然后:

  1. 更新镜像到 nginx:1.21
  2. 查看滚动状态
  3. 回滚到之前的版本
<details> <summary>查看答案</summary>
# 1. 创建 Deployment
kubectl create deployment web-app --image=nginx:1.19 --replicas=3

# 2. 等待就绪
kubectl rollout status deployment/web-app

# 3. 更新镜像
kubectl set image deployment/web-app nginx=nginx:1.21

# 4. 查看滚动状态
kubectl rollout status deployment/web-app

# 5. 查看历史
kubectl rollout history deployment/web-app

# 6. 回滚
kubectl rollout undo deployment/web-app

# 7. 验证
kubectl describe deployment web-app | grep Image
</details>

题目 6(排查题)

一个 Pod 处于 CrashLoopBackOff 状态,请列出你的排查步骤:

<details> <summary>查看答案</summary>
# 第 1 步:看 Pod 状态和重启次数
kubectl get pod <pod-name>

# 第 2 步:看上次崩溃前的日志(最关键)
kubectl logs <pod-name> --previous

# 第 3 步:看 Pod 详情和事件
kubectl describe pod <pod-name>

# 第 4 步:根据日志判断原因
# - OOMKilled → 增加 memory limits
# - 配置错误 → 检查环境变量和 ConfigMap
# - 镜像问题 → 检查 command 和 args
# - 健康检查失败 → 调整 liveness probe

排查口诀:logs previous → describe → events,三步定位。

</details>

📋 本章小结

核心资源速查

资源创建命令用途一句话记忆
Podkubectl run运行容器"Kubernetes 的最小工作单元"
Deploymentkubectl create deployment管理无状态应用"应用的运营经理,管更新管回滚"
ReplicaSet自动由 Deployment 创建维持 Pod 副本数"排班表,永远保证够人"
Namespacekubectl create namespace资源隔离"楼层,互不干扰"

高频命令速查

操作命令一句话记忆
生成 YAML--dry-run=client -o yaml"生成模板不创建"
强制删除--force --grace-period=0"秒删不等待"
查看崩溃日志logs --previous"看上一轮的遗言"
切换命名空间config set-context --current --namespace="每题第一步"
滚动更新set image deployment/NAME CONTAINER=IMAGE"边跑边换"
回滚rollout undo deployment/NAME"一键恢复"
查看字段文档explain pod.spec.containers"忘了怎么写就问它"

考试要点速记

Pod 创建:kubectl run NAME --image=IMAGE
Deployment:kubectl create deployment NAME --image=IMAGE
生成 YAML:--dry-run=client -o yaml
强制删除:--force --grace-period=0
查看日志:kubectl logs [-f] [--previous]
进入容器:kubectl exec -it POD -- /bin/sh
滚动更新:kubectl set image deployment/NAME CONTAINER=IMAGE
回滚:kubectl rollout undo deployment/NAME
切换 NS:kubectl config set-context --current --namespace=NAME
排查三板斧:describe → logs --previous → get events
📝 章节练习 (15 题)
开始练习