k8s-pod简介
摘要: Pod是Kubernetes中最小的调度和运行单元,本质是包裹容器的逻辑组,共享网络(同一IP)和存储(Volume)。一个Pod包含基础设施容器(pause)、业务容器和可选的Init容器。常见Pod状态包括Pending、CrashLoopBackOff等,排查时需结合kubectl get/describe/logs命令分析Events日志和容器状态。典型问题如ImagePullBa
一、Pod 到底是什么?(最核心定义)
Pod = Kubernetes 中最小的调度 / 运行单元
- 它不是容器,是一层包裹容器的 “逻辑组”
- 一个 Pod 里可以放 1 个或多个紧密相关的容器
- K8s 永远不会直接调度容器,只会调度 Pod
大白话比喻
- 容器 = 一个独立的小盒子
- Pod = 一组共享 “房间、网络、柜子” 的小盒子组合
- K8s = 只按 “房间(Pod)” 分配机器,不按 “盒子(容器)” 分配
二、Pod 的 2 个核心共享特性(必须懂)
同一个 Pod 里的所有容器,完全共享两样东西:
1. 共享网络(同一个 IP)
- 整个 Pod 只有 1 个 IP
- 容器之间用
localhost就能互相访问 - 端口不能冲突
2. 共享存储(Volume)
- 可以挂同一个目录 / 磁盘
- 容器 A 写的文件,容器 B 能直接读
这就是为什么日志容器、监控容器、业务容器适合放同一个 Pod。
三、Pod 内部结构(你部署时卡在这里过)
一个标准 Pod 由三部分组成:
1. 基础设施容器:pause(最关键!)
就是你之前报错拉取不到的:
plaintext
registry.k8s.io/pause:3.8
作用:
- 给整个 Pod 提供网络命名空间
- 分配 Pod IP
- 所有业务容器共享它的网络
- 只要 Pod 存在,pause 就存在
2. 业务容器(App Container)
- 真正跑服务的容器(Nginx、MySQL、Java、Calico、apiserver)
- 你看到的
Running/Crash都是指它们
3. Init 容器(初始化容器)
- 在业务容器之前运行
- 用于初始化:等待依赖、拉配置、建表、预热
- 你看到的状态:
plaintext
就是它在拉镜像或执行初始化Init:ImagePullBackOff Init:0/1
四、Pod 的生命周期(运行流程)
- Pending:正在调度、拉镜像、初始化
- ContainerCreating:创建容器
- Running:正常运行
- Succeeded:正常退出(一次性任务)
- Failed:异常退出
- Unknown:失联(节点挂了)
五、你最常遇到的 Pod 状态(全是你踩过的坑)
1. Pending
- 还没分配到节点
- 或资源不足
- 或依赖没准备好
2. ContainerCreating
- 正在拉镜像 / 创建容器
3. ImagePullBackOff
- 镜像拉不到(网络、仓库、权限、tag 错)
- 你装 Calico 时遇到的就是这个
4. CrashLoopBackOff
- 容器启动后立刻崩溃
- K8s 反复重启
- 常见:配置错、端口被占、启动命令错
5. Running
- 正常运行
6. Completed
- 一次性任务执行完退出(Job)
六、静态 Pod vs 普通 Pod(你 Master 上全是静态 Pod)
1. 静态 Pod(Static Pod)
- 由 kubelet 直接管理
- 配置文件放在:
plaintext
/etc/kubernetes/manifests/ - 不受控制器管理
- 你 Master 上的核心组件全是:
- kube-apiserver
- etcd
- kube-controller-manager
- kube-scheduler
2. 普通 Pod
- 由 Deployment、DaemonSet、StatefulSet 管理
- 比如 Nginx、Calico、业务应用
七、最常用的 Pod 操作命令(你马上能用)
bash
运行
# 查看所有 Pod
kubectl get pods
# 查看指定命名空间(Calico、apiserver 都在这里)
kubectl get pods -n kube-system
# 看详细信息(排查错误神器)
kubectl describe pod <pod名> -n kube-system
# 看容器日志
kubectl logs <pod名> -n kube-system
# 实时日志
kubectl logs -f <pod名> -n kube-system
# 进入 Pod 内部
kubectl exec -it <pod名> -- /bin/bash
# 删除 Pod(控制器会自动重建)
kubectl delete pod <pod名>
八、Pod 的重要特点(生产 / 面试都考)
- Pod 是临时的:删了就没了,IP 会变
- 不能直接用裸 Pod:必须用 Deployment/DaemonSet 管理
- 不能跨节点扩容:一个 Pod 只在一台节点上
- 自愈靠控制器:Pod 自己不会自愈,是 Deployment 帮它重启
- 网络必须靠 CNI:没装 Calico/Flannel,Pod 没有 IP,节点永远 NotReady
九、给你总结成一句最关键的话
Pod = K8s 最小运行单位,里面一定有一个 pause 沙箱容器 + 业务容器,共享网络和存储,所有调度、自愈、网络、存储都围绕 Pod 展开。
你之前部署 K8s 遇到的几乎所有问题:
- pause 镜像拉取失败
- Calico 启动不了
- apiserver 起不来
- 节点 NotReady
- ImagePullBackOff
本质全是 Pod 启动失败。
第一步:先看 Pod 基础状态(10 秒定位异常类型)
先执行最基础的命令,快速判断 Pod 异常的 “大方向”,避免盲目排查:
# 查看目标命名空间的Pod(比如kube-system,你的Calico/apiserver都在这)
kubectl get pods -n kube-system -o wide
# 若想只看异常Pod,用grep过滤(排除Running/Completed)
kubectl get pods -n kube-system | grep -v -E "Running|Completed"
关键状态解读(对应你踩过的坑)
| 状态 | 核心原因(快速判断) | 你遇到的场景 |
|---|---|---|
Pending |
Pod 未调度到节点(资源不足 / 调度规则冲突) | Calico-kube-controllers Pending |
Init:ImagePullBackOff |
初始化容器拉取镜像失败 | Calico-node 启动失败 |
ImagePullBackOff |
业务容器拉取镜像失败 | 任何 Pod 都可能遇到(国内网络) |
CrashLoopBackOff |
容器启动后立刻崩溃(配置 / 命令 / 依赖错) | apiserver/etcd 异常重启 |
ContainerCreating |
容器正在创建(拉镜像 / 挂载存储) | 刚部署 Pod 时的过渡状态 |
Unknown |
节点失联(kubelet 挂了 / 节点宕机) | 若节点 NotReady 可能出现 |
示例:你之前的calico-node-79nm9 0/1 Init:ImagePullBackOff,一眼就能判断是 “初始化容器拉镜像失败”,不用再查其他。
第二步:查 Pod 详细描述(找核心错误信息,最关键)
kubectl describe是排查 Pod 异常的 “神器”,能看到 Pod 从创建到现在的所有事件、资源配置、容器状态,重点看Events部分(K8s 会记录 Pod 的每一步操作和错误)。
# 查异常Pod的详细信息(替换<Pod名>为实际名称,比如calico-node-79nm9)
kubectl describe pod <Pod名> -n kube-system
重点看这 3 个部分(按优先级)
1. 最关键:Events(事件日志)
K8s 会把 Pod 的 “调度、拉镜像、启动容器” 等所有操作记录在这里,错误信息直接显示:
# 你之前遇到的ImagePullBackOff,Events里会显示:
Events:
Type Reason Age From Message
---- ------ ---- ---- -------
Normal Scheduled 10m default-scheduler Successfully assigned kube-system/calico-node-79nm9 to k8s-master
Warning Failed 8m (x4 over 9m) kubelet Failed to pull image "calico/node:v3.25.1": rpc error: code = Unknown desc = failed to pull and unpack image "docker.io/calico/node:v3.25.1": failed to resolve reference "docker.io/calico/node:v3.25.1": failed to do request: Head "https://registry-1.docker.io/v2/calico/node/manifests/v3.25.1": dial tcp 140.82.112.20:443: connect: connection refused
Warning Failed 8m (x4 over 9m) kubelet Error: ErrImagePull
Normal BackOff 8m (x6 over 9m) kubelet Back-off pulling image "calico/node:v3.25.1"
Warning Failed 7m (x7 over 9m) kubelet Error: ImagePullBackOff
一眼就能看出:拉取 docker.io 的 calico 镜像失败,原因是国内网络连不上。
2. 次关键:Init Containers(初始化容器状态)
如果是Init:开头的异常,看这里的State和Last State,会显示初始化容器的失败原因:
Init Containers:
install-cni:
Container ID:
Image: calico/cni:v3.25.1
Image ID:
State: Waiting
Reason: ImagePullBackOff
Last State: Terminated
Reason: Error
Exit Code: 1
3. 补充:Containers(业务容器状态)
看业务容器的Image(镜像地址是否正确)、Command(启动命令是否错)、Resources(资源限制是否不够)。
第三步:查容器日志(定位运行时错误)
如果 Pod 已经创建了容器(哪怕崩溃了),查日志能看到容器启动 / 运行时的具体错误,比如 apiserver 连不上 etcd、配置文件错误等。
1. 查普通运行中 / 崩溃容器的日志
# 查业务容器日志(替换<Pod名>,比如kube-apiserver-k8s-master)
kubectl logs <Pod名> -n kube-system
# 实时跟踪日志(排查动态错误,比如apiserver超时)
kubectl logs -f <Pod名> -n kube-system
# 若Pod里有多个容器,指定容器名(比如calico-node里的calico-node容器)
kubectl logs <Pod名> -n kube-system -c <容器名>
# 查崩溃容器的上一次日志(关键!容器重启后,用--previous看上次错误)
kubectl logs <Pod名> -n kube-system --previous
2. 查 Init 容器(初始化容器)的日志
# 查Init容器日志(指定-init容器名,比如install-cni)
kubectl logs <Pod名> -n kube-system -c <Init容器名>
示例:你之前 apiserver 超时,查日志会看到:
E0210 18:03:56.831778 46508 kubelet_node_status.go:92] "Unable to register node with API server" err="Post \"https://192.168.200.10:6443/api/v1/nodes\": dial tcp 192.168.200.10:6443: connect: connection refused" node="k8s-master"
直接定位:apiserver 还没就绪,kubelet 注册节点失败。
第四步:针对性解决常见 Pod 异常(对应你的坑)
根据前 3 步的排查结果,对应解决最常见的 5 类异常:
场景 1:ImagePullBackOff(你最常遇到)
- 根因:镜像源不可达(国外仓库)、镜像 tag 错误、镜像仓库权限问题
- 解决方法:
- 换国内镜像源(腾讯云 / 阿里云):比如把
calico/node:v3.25.1换成mirror.ccs.tencentyun.com/calico/node:v3.25.1; - 手动拉取镜像并打 tag(兜底):
sudo ctr -n k8s.io images pull mirror.ccs.tencentyun.com/calico/node:v3.25.1 sudo ctr -n k8s.io images tag mirror.ccs.tencentyun.com/calico/node:v3.25.1 calico/node:v3.25.1 - 检查镜像 tag 是否正确(比如 v3.25.1 写成 3.25)。
- 换国内镜像源(腾讯云 / 阿里云):比如把
场景 2:CrashLoopBackOff
- 根因:启动命令错误、配置文件错误、端口被占用、资源不足
- 解决方法:
- 查
kubectl logs <Pod名> --previous看崩溃原因; - 检查 Pod 的启动命令(
Command/Args)是否正确; - 调整资源限制(比如给 apiserver 加内存):
resources: requests: cpu: 100m memory: 256Mi limits: cpu: 1000m memory: 1Gi
- 查
场景 3:Pending
- 根因:节点资源不足(CPU / 内存不够)、调度规则冲突、节点污点(NoSchedule)
- 解决方法:
- 查
kubectl describe pod <Pod名>的 Events,看是否有 “Insufficient cpu/memory”; - 查看节点资源:
kubectl top node; - 移除节点污点(如果是 Master 节点被标记为不可调度):
kubectl taint nodes k8s-master node-role.kubernetes.io/control-plane:NoSchedule-
- 查
场景 4:Init:Error(初始化容器失败)
- 根因:初始化容器执行命令失败、依赖服务未就绪(比如等 etcd 启动)
- 解决方法:
- 查 Init 容器日志:
kubectl logs <Pod名> -c <Init容器名>; - 等待依赖服务就绪(比如等 apiserver/etcd 启动);
- 重新执行初始化容器:删除 Pod 让控制器重建(
kubectl delete pod <Pod名> -n kube-system)。
- 查 Init 容器日志:
场景 5:Pod 运行正常但节点 NotReady
- 根因:CNI 网络插件未就绪(Calico/Flannel Pod 异常)、kube-proxy 未运行
- 解决方法:
- 查 Calico Pod 状态:
kubectl get pods -n kube-system | grep calico; - 确保 Calico Pod 全部 Running;
- 检查节点网络:
ip a看是否有 calico 相关网卡(calixxx)。
- 查 Calico Pod 状态:
兜底排查(以上都没用时)
如果按上面步骤还没解决,查集群底层组件:
# 1. 检查节点状态
kubectl get nodes
# 2. 检查kubelet状态(Pod的“管理者”)
sudo systemctl status kubelet
# 3. 检查containerd状态(容器运行时)
sudo systemctl status containerd
# 4. 查看kubelet实时日志(找底层错误)
sudo journalctl -u kubelet -f --no-pager更多推荐


所有评论(0)