2. Kubernetes Deployment 基础:Deployment 工作原理、ReplicaSet 与 Pod 的关系、版本管理机制
2.1 Deployment 工作原理
Deployment 是 Kubernetes 中最常用的工作负载 API 对象,它提供了声明式的 Pod 和 ReplicaSet 更新能力。其核心设计理念是“通过控制器模式驱动实际状态向期望状态收敛”。
Deployment 控制器的工作流程可概括为以下步骤:
- 监听与比对:控制器通过 Informer 机制监听 Deployment、ReplicaSet、Pod 的资源变化,持续比对
spec.replicas与当前集群中对应 Pod 的数量。 - 版本协调:当 Deployment 的
spec.template发生变化(如镜像版本更新)时,控制器会创建新的 ReplicaSet,并逐步缩容旧的 ReplicaSet。 - 滚动更新:按照
spec.strategy.rollingUpdate中定义的maxSurge和maxUnavailable参数,控制 Pod 的替换速率。 - 状态持久化:将当前的版本号、可用副本数、更新进度等状态写入
status字段,供外部监控或调度系统读取。
关键设计原则: Deployment 不直接管理 Pod,而是通过管理 ReplicaSet 来间接控制 Pod 的生命周期。这种分层设计使得版本回滚、金丝雀发布等高级策略成为可能。
2.2 ReplicaSet 与 Pod 的关系
ReplicaSet 是 Deployment 与 Pod 之间的中间层,其核心职责是确保指定数量的 Pod 副本始终运行。理解三者之间的关系是掌握版本管理的基础。
| 对象 | 职责 | 与上层关系 | 与下层关系 |
|---|---|---|---|
| Deployment | 声明式更新、版本管理、回滚 | 管理 ReplicaSet | 不直接管理 Pod |
| ReplicaSet | 确保 Pod 副本数、Pod 模板快照 | 被 Deployment 管理 | 通过 spec.selector 匹配并管理 Pod |
| Pod | 运行容器实例 | 被 ReplicaSet 管理 | 通过 metadata.ownerReferences 关联 ReplicaSet |
版本漂移的根源: 当 Deployment 的
spec.template 被修改时,控制器会创建一个新的 ReplicaSet(新版本),而旧的 ReplicaSet 仍然保留。如果多个 ReplicaSet 同时拥有匹配的 Pod,就会产生“版本漂移”现象——即集群中同时运行着不同版本的 Pod。
ReplicaSet 通过 spec.selector.matchLabels 来识别其管理的 Pod。每个 Pod 在创建时会被打上对应的标签,并设置 ownerReferences 指向所属的 ReplicaSet。这种基于标签的松耦合关系,使得 ReplicaSet 可以灵活地接管或释放 Pod。
2.3 版本管理机制
Kubernetes Deployment 的版本管理机制基于 ReplicaSet 的历史记录。每次 Deployment 的 spec.template 发生变化时,控制器都会创建一个新的 ReplicaSet,并将旧的 ReplicaSet 保留在历史记录中。
2.3.1 版本号与修订历史
Deployment 使用 metadata.generation 和 status.observedGeneration 来跟踪期望状态的变更次数。每次 spec.template 的变更都会递增 generation。同时,spec.revisionHistoryLimit 控制保留的历史 ReplicaSet 数量(默认 10)。
# 查看 Deployment 的修订历史
kubectl rollout history deployment/my-app
# 输出示例
REVISION CHANGE-CAUSE
1 <none>
2 <none>
3 kubectl set image deployment/my-app my-app=nginx:1.21
2.3.2 回滚机制
当需要回滚到某个历史版本时,Deployment 控制器会执行以下操作:
- 查找目标 ReplicaSet:根据指定的 revision 找到对应的 ReplicaSet。
- 复制 Pod 模板:将目标 ReplicaSet 的
spec.template复制到 Deployment 的spec.template中。 - 触发更新:由于
spec.template发生变化,控制器会创建新的 ReplicaSet(其 Pod 模板与目标版本一致),并逐步缩容当前活跃的 ReplicaSet。
版本漂移风险: 在跨集群场景中,如果两个集群的 Deployment 版本不同步(例如集群 A 回滚到 v1,而集群 B 仍停留在 v2),当流量被调度到不同集群时,用户可能会访问到不同版本的应用,导致行为不一致。这是本课程后续章节要重点解决的问题。
2.3.3 版本管理关键参数
| 参数 | 位置 | 说明 | 默认值 |
|---|---|---|---|
revisionHistoryLimit |
spec.revisionHistoryLimit |
保留的历史 ReplicaSet 数量 | 10 |
change-cause |
Annotation: kubernetes.io/change-cause |
记录变更原因,便于审计 | 无 |
generation |
metadata.generation |
期望状态的版本号,每次 spec 变更递增 | 1 |
observedGeneration |
status.observedGeneration |
控制器实际处理到的 generation | 0 |
2.3.4 版本漂移的典型场景
在单集群中,版本漂移通常由以下原因引起:
- 手动修改 Pod 标签:直接修改 Pod 的标签,使其脱离 ReplicaSet 的管理范围,导致 ReplicaSet 创建新的 Pod 来补足副本数。
- 直接修改 ReplicaSet:绕过 Deployment 直接修改 ReplicaSet 的 Pod 模板,导致与 Deployment 的期望状态不一致。
- 并发更新冲突:多个用户或 CI/CD 系统同时更新同一个 Deployment,导致控制器交替创建不同的 ReplicaSet。
预防策略的核心思路: 在跨集群调度场景中,需要通过版本一致性校验、调度策略约束和自动化同步机制,确保所有集群中的 Deployment 版本保持一致,从而避免版本漂移带来的服务不一致问题。