【K8s】基础必知系列(一)
本专栏文章持续更新,新增内容使用蓝色表示。
一、容器运行时演进:从 Docker 到 Containerd
1.1 容器运行时的发展历程
关于"K8s 在 1.20 之后就不再支持 Docker"的说法不完全准确。实际情况是 Kubernetes 不再直接内置对 Docker 的支持,但用户仍然可以通过 CRI(容器运行时接口)来管理 Docker 容器。
主要基于两个重要原因:
生态兼容性考量:Docker 商业化后与开源生态的兼容性考虑;
维护成本优化:官方维护 dockershim 适配器的成本较高。
1.2 当前容器运行时方案
继续使用 Docker
可以通过第三方适配器如 cri-dockerd,它实现了 CRI 接口,将 Kubernetes 的指令翻译成 Docker API 调用。
直接使用 Containerd
在 K8s 1.24 之后,更推荐直接使用 containerd,优势如下:
-
架构简洁:containerd 是 Docker 的底层运行时,去除中间层提升效率
-
原生支持:containerd 原生实现 CRI 接口,无需额外适配器
-
符合标准:更贴近云原生生态系统标准
-
资源消耗:更少的资源占用,更高的性能表现
二、Kubernetes 集群搭建过程
首先要规划节点数量,比较推荐准备至少3个控制节点和2个工作节点以保证高可用。
然后对所有节点进行统一处理:安装容器运行时(如containerd)、关闭Swap、加载内核模块。并且安装kubeadm、kubelet和kubectl。
初始化控制平面,在第一个Master节点上使用kubeadm init命令去初始化集群,然后配置kubectl。
完成之后需要安装网络插件,比如Calico、flannel等,以保证正常的通信。
最后让节点使用kubeadm join命令加入集群,验证状态。
为什么必须关闭 Swap?
性能层面的考量:
-
交换操作涉及磁盘 I/O,速度比内存慢几个数量级
-
启用 Swap 可能导致性能"抖动"现象,影响容器运行稳定性
-
容器环境对 I/O 性能要求极高,Swap 会显著降低整体性能
资源管理的影响:
-
调度器基于物理内存进行决策,Swap 会干扰调度准确性
-
破坏 Pod 驱逐机制,可能导致 OOM Killer 误杀重要进程
-
掩盖内存泄漏问题,增加故障排查难度
特殊场景的处理方案
对于确实需要 Swap 的应用场景:
# 修改 kubelet 配置
--fail-swap-on=false
# 优化内核参数
echo 'vm.swappiness=1' >> /etc/sysctl.conf
echo 'vm.min_free_kbytes=总内存的2-3%' >> /etc/sysctl.conf
sysctl -p
可参考链接:
Tuning Linux Swap for Kubernetes: A Deep Dive | Kubernetes
Kubernetes 1.28:在 Linux 上使用 swap 的 Beta 支持 |Kubernetes
网络插件的重要性
kubeadm init 后必须立即部署网络插件的原因:
-
Pod 网络通信:为 Pod 提供唯一的 IP 地址和网络连通性
-
服务发现:支持 Service 网络和 DNS 解析
-
网络策略:实现网络安全控制策略
-
跨节点通信:确保不同节点上的 Pod 可以互相通信
三、Kubernetes 网络架构
3.1 网络模型与 CNI 机制
Kubernetes 通过扁平化网络模型和 CNI 为 Pod 提供网络服务:
核心网络特性:
-
每个 Pod 拥有唯一的 IP 地址
-
Pod 间无需 NAT 即可直接通信
-
通过 CNI 插件实现具体网络功能
-
支持网络策略和访问控制
3.2 主流网络插件对比
3.2.1 Flannel
技术原理:创建 Overlay 网络,通过 VXLAN 或 host-gw 实现跨节点通信
核心优势:对底层网络无特殊要求,部署简单快捷
适用场景:快速部署、网络环境复杂的场景
性能特点:有一定的封包开销,但稳定性较好
3.2.2 Calico
技术原理:基于 BGP 协议的直接路由,无封包开销
核心优势:性能接近物理网络,支持强大的网络策略
适用场景:对性能和安全性要求高的生产环境
扩展能力:支持大规模集群部署
3.3 网络通信机制详解
3.3.1 同一节点 Pod 通信
CNI 插件创建虚拟网桥(如 cni0),连接节点上的所有 Pod,类似物理交换机的工作方式。
br-netfilter 的关键作用:
确保经过网桥的数据包也能被 iptables 规则过滤,这是 Service 网络正常工作的基础。
3.3.2 跨节点 Pod 通信的两种模式
Overlay 网络(Flannel):
Pod A → 封包(VXLAN)→ 节点网络 → 解包 → Pod B
封装开销 透明传输 解封装
直接路由(Calico):
Pod A → 路由表 → 物理网络 → 路由表 → Pod B
BGP学习路由 直接传输 BGP发布路由
3.4 Calico 与 CRD
Calico 大量使用 CRD 实现高级网络功能:
-
NetworkPolicy:定义精细的 Pod 间访问控制规则
-
GlobalNetworkPolicy:集群级别的网络安全策略
-
IPPool:IP 地址池的动态管理
-
BGPConfiguration:BGP 路由协议的详细配置
相比之下,Flannel 基本不使用 CRD,其设计定位更专注于基础网络连通性,这也是两者在架构哲学上的根本差异。
四、CRD
4.1 基础概念
CRD(Custom Resource Definition) 是 Kubernetes 的核心扩展机制,它允许用户自定义资源类型,就像内置的 Pod、Service 一样。
核心组件关系:
-
CRD:定义资源结构的模板,包括字段规范和验证规则
-
CR:根据 CRD 模板创建的具体资源配置实例
-
Controller:监听 CR 变化并执行相应运维操作的控制器
4.2 生态价值
平台扩展性:使 Kubernetes 从容器编排平台演进为真正的"云原生操作系统";
统一管理界面:通过统一的 kubectl 工具管理所有自定义资源;
运维自动化:催生 Operator 模式,实现复杂应用的全生命周期管理;
生态集成:为第三方工具提供标准的集成接口。
4.3 应用场景
| 场景类型 | 典型实现 | 核心价值 |
|---|---|---|
| 数据库管理 | MySQL Operator, Redis Operator | 有状态应用的自动化运维 |
| 监控告警 | Prometheus ServiceMonitor | 声明式监控配置 |
| 网络策略 | Calico NetworkPolicy | 精细化网络访问控制 |
| CI/CD | Tekton Pipeline | 流水线即代码 |
| 备份恢复 | Velero Backup | 跨云灾备方案 |
五、Pod
Pod 作为 Kubernetes 的最小调度单元,体现了重要的设计理念:
-
逻辑分组:Pod 是容器的逻辑组合,代表一个完整的应用实例
-
共享环境:容器间共享网络、存储和生命周期
-
调度原子性:Pod 内的容器总是被调度到同一个节点
5.1 Pause 容器的关键作用
Pause 容器,又称 "infra" 容器,是每个 Pod 中第一个启动的容器,为 Pod 提供底层基础设施支持。
-
命名空间管理:提供共享的 network、IPC、PID 命名空间
-
资源驻留:保持 Pod 网络和存储资源的持续存在
-
僵尸进程回收:作为 PID 1 进程回收僵尸进程
Pause 容器在 Pod 中的角色类似于 Linux 系统中的 systemd——它不运行具体应用,而是为其他进程提供稳定的运行环境和生命周期管理
5.2 Pod 生命周期
Pending:已接受请求,等待调度和镜像拉取
ContainerCreating:正在创建容器运行时环境
Running:至少一个主容器正常运行
Succeeded:所有容器成功完成任务并退出
Failed:至少一个容器异常退出
Terminating:正在执行优雅终止流程

5.4 静态 Pod
由 kubelet 直接管理的特殊 Pod 类型:
管理方式:通过节点本地静态配置文件定义
监控机制:API Server 通过镜像 Pod 间接监控状态
命名规范:自动添加节点主机名后缀避免冲突
使用场景:集群核心组件部署,如 etcd、kube-proxy
六、核心组件
6.1 管理工具组件
| 组件 | 核心职责 | 关键特性 |
|---|---|---|
| kubeadm | 集群生命周期管理 | init/join/upgrade 命令 |
| kubectl | 集群交互命令行工具 | 声明式资源管理 |
| kubelet | 节点代理和容器运行时接口 | Pod 生命周期管理 |
| kube-proxy | 服务发现和负载均衡 | iptables/ipvs 规则管理 |
6.2 控制平面组件
| 组件 | 核心职责 | 高可用方案 |
|---|---|---|
| kube-apiserver | 统一 API 接口和认证鉴权 | 多实例负载均衡 |
| etcd | 分布式元数据存储 | 集群化部署 |
| kube-controller-manager | 状态协调和故障恢复 | 领导者选举 |
| kube-scheduler | 资源调度决策 | 多副本部署 |
6.3 Pod 创建过程

首先,用户通过 kubectl 提交 Pod 配置,kube-apiserver 对其进行验证后,将元数据作为“期望状态”写入 etcd,此时 Pod 状态为 Pending。
接着,kube-scheduler (通过 List-watch 机制)监听到这个未调度的 Pod,通过调度算法为其选择最合适的节点,并将绑定信息通过 kube-apiserver 更新回 etcd。
最后,目标节点上的 kubelet 监听到该 Pod 的绑定事件,调用容器运行时创建容器,并将最终的 Running 状态汇报给 kube-apiserver,由其再次写入 etcd,完成整个流程。
注意:
kube-controller-manager 不参与:此流程适用于直接创建单个 Pod(kind: Pod)。当创建 Deployment 等控制器资源时,kube-controller-manager 中的相应控制器才会介入,确保实际的 Pod 副本数与期望值一致。
etcd 是唯一状态源:整个过程中,所有状态的变更都经由 kube-apiserver 持久化到 etcd,确保了集群状态的一致性和可追溯性。
List-Watch 机制:kube-scheduler 和 kubelet 通过监听 kube-apiserver 的事件来触发相应操作,这是一种高效的、声明式的协同工作模式。
6.4 调度策略与节点选择
调度器基于多维度因素进行智能决策:
-
资源需求匹配:CPU、内存、存储的资源请求和限制
-
亲和性规则:节点亲和性、Pod 亲和性/反亲和性
-
污点与容忍度:节点的排斥机制与 Pod 的接受能力
-
拓扑分布约束:保证工作负载在集群中的合理分布
-
自定义策略:通过调度器扩展实现业务特定需求
如有问题或建议,欢迎在评论区中留言~
更多推荐


所有评论(0)