rollout 与 rolling update 的区别

This article is extracted from the chat log with AI. Please identify it with caution.

本文边界:本文聚焦发布过程、rollout 操作与 RollingUpdate 策略的区别;Deployment 的资源模型及 Service/Deployment 的选型边界请阅读配套文章。

推荐深读Deployment 详解:Kubernetes 集群的"应用部署控制器"什么时候用 Service,什么时候用 Deployment

说明:本文由 Codex 根据作者提供的主题、素材与公开资料辅助生成,属于 AI 生成/整理内容,非作者原创。请读者自行甄别并交叉验证。

先说结论#

rolloutrolling update 不是同一层概念。

可以先这样记:

rolling update 是一种更新策略;
rollout 是一次发布过程,以及 kubectl 用来观察和管理这个过程的一组命令。

在 Deployment 场景里:

修改 Deployment 的 Pod template
触发一次 rollout
Deployment 按 strategy 执行更新
如果 strategy 是 RollingUpdate,就进行滚动更新

所以 rolling update 是 rollout 过程中可能采用的一种方式。

rollout 是什么#

rollout 更像是“发布过程”。

当 Deployment 的 Pod 模板发生变化时,会触发一次新的 rollout。

常见会触发 rollout 的变化:

  • 修改容器镜像。
  • 修改容器启动参数。
  • 修改环境变量。
  • 修改 Pod template 下的 labels / annotations。
  • 修改 readinessProbe / livenessProbe。
  • 修改 resources。

不会触发 rollout 的变化:

  • 只修改 Deployment 的副本数。
  • 只修改不属于 .spec.template 的字段。

核心判断标准是:

Deployment 的 .spec.template 是否变化。

例如:

kubectl set image deployment/web web=nginx:1.27

这会修改 Pod template 里的镜像,因此触发 rollout。

再比如:

kubectl scale deployment/web --replicas=5

这只是修改副本数,不会创建新的 Deployment revision。

kubectl rollout 命令#

kubectl rollout 是管理 rollout 的命令入口。

常见子命令:

kubectl rollout status deployment/web
kubectl rollout history deployment/web
kubectl rollout undo deployment/web
kubectl rollout pause deployment/web
kubectl rollout resume deployment/web
kubectl rollout restart deployment/web

这些命令不是更新策略本身,而是观察和操作发布过程。

命令作用
status查看 rollout 是否完成
history查看 revision 历史
undo回滚到上一个或指定 revision
pause暂停 rollout
resume恢复 rollout
restart触发一次重启式 rollout

kubectl rollout 可以用于 Deployment、DaemonSet、StatefulSet 等资源,但不同资源的更新语义会有差异。

rolling update 是什么#

rolling update 是滚动更新。

它的目标是:

不要一次性杀掉所有旧 Pod;
逐步创建新 Pod;
逐步删除旧 Pod;
尽量保持服务可用。

Deployment 默认更新策略就是 RollingUpdate

示例:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: web
spec:
  replicas: 4
  strategy:
    type: RollingUpdate
    rollingUpdate:
      maxUnavailable: 1
      maxSurge: 1
  selector:
    matchLabels:
      app: web
  template:
    metadata:
      labels:
        app: web
    spec:
      containers:
        - name: web
          image: nginx:1.27
          ports:
            - containerPort: 80

这里的意思是:

  • 期望副本数是 4。
  • 更新过程中最多允许 1 个 Pod 不可用。
  • 更新过程中最多允许额外多创建 1 个 Pod。

滚动过程大致是:

旧 RS: 4, 新 RS: 0
旧 RS: 4, 新 RS: 1
旧 RS: 3, 新 RS: 1
旧 RS: 3, 新 RS: 2
旧 RS: 2, 新 RS: 2
...
旧 RS: 0, 新 RS: 4

Deployment Controller 会根据 maxUnavailablemaxSurge 控制这个节奏。

Deployment、ReplicaSet 和 revision#

Deployment 并不直接管理每个 Pod。

它通过 ReplicaSet 来管理不同版本的 Pod 模板。

一次 rollout 通常对应一个新的 ReplicaSet:

Deployment
  ├── ReplicaSet old: nginx:1.26
  └── ReplicaSet new: nginx:1.27

当镜像从 nginx:1.26 改到 nginx:1.27

1. Deployment 发现 Pod template 变化
2. 创建新的 ReplicaSet
3. 按 rolling update 策略放大新 ReplicaSet
4. 按 rolling update 策略缩小旧 ReplicaSet
5. rollout 完成后,新 ReplicaSet 达到期望副本数

查看 ReplicaSet:

kubectl get rs -l app=web

查看 revision:

kubectl rollout history deployment/web
kubectl describe deployment web

revision 只在 Pod template 变化时创建。

另一个策略:Recreate#

Deployment 还有另一种策略:Recreate

spec:
  strategy:
    type: Recreate

它的行为更直接:

先删除所有旧 Pod;
再创建新 Pod。

这会带来停机窗口,但有些场景反而需要这样:

  • 应用不支持新旧版本同时运行。
  • 多副本同时写同一份状态会出问题。
  • 旧版本必须完全退出后,新版本才能启动。
  • 开发测试环境不关心短暂停机。

所以 rollout 不一定总是 rolling update。

rollout 是发布过程;
RollingUpdate / Recreate 是 Deployment 执行发布的策略。

rollout restart 是什么#

kubectl rollout restart deployment/web 经常被误解。

它不是把 Deployment “重启”成一个特殊状态,而是通过修改 Pod template 的 annotation 来触发一次新的 rollout。

效果类似:

Deployment Pod template 变化
创建新 revision
旧 Pod 逐步被新 Pod 替换

常见用途:

  • 重新读取 ConfigMap 或 Secret。
  • 重新拉取同 tag 镜像。
  • 让 Pod 重新建立连接。
  • 触发应用进程重启。

示例:

kubectl rollout restart deployment/web
kubectl rollout status deployment/web

如果应用需要优雅退出,仍然要配合:

  • readinessProbe。
  • preStop。
  • SIGTERM 处理。
  • terminationGracePeriodSeconds。
  • PodDisruptionBudget。

rollout restart 只负责触发替换,不保证应用层 shutdown 一定正确。

回滚怎么理解#

回滚是 rollout 管理的一部分。

kubectl rollout undo deployment/web

默认回滚到上一个 revision。

也可以指定 revision:

kubectl rollout undo deployment/web --to-revision=2

回滚的本质通常是:

把 Deployment 的 Pod template 改回历史 revision 对应的模板;
再触发一次新的 rollout。

注意:

  • 只有保留了旧 ReplicaSet,才有回滚基础。
  • revisionHistoryLimit 会影响可回滚历史数量。
  • 如果镜像 tag 是可变 tag,例如 latest,回滚不一定真的回到旧镜像内容。

生产环境建议使用不可变镜像 tag 或 digest。

排查 rollout#

常用命令:

kubectl rollout status deployment/web
kubectl rollout history deployment/web
kubectl describe deployment web
kubectl get rs -l app=web
kubectl get pod -l app=web -o wide
kubectl get events --sort-by=.metadata.creationTimestamp

看 Deployment 状态:

kubectl get deployment web

常见字段:

字段含义
READY当前 Ready Pod 数 / 期望 Pod 数
UP-TO-DATE已经更新到新模板的 Pod 数
AVAILABLE可用 Pod 数
AGE资源存在时间

如果 rollout 卡住,常见原因是:

  • 新镜像拉取失败。
  • readinessProbe 不通过。
  • 资源不足,Pod Pending。
  • Deployment selector 和 template labels 不匹配。
  • 应用启动失败或 CrashLoopBackOff。
  • PDB、调度约束、节点资源导致替换困难。
  • progressDeadlineSeconds 超时。

常见误区#

rolling update 等于 rollout#

不等于。

rolling update 是策略;rollout 是发布过程和管理入口。

只要 scale 就会产生 revision#

不会。

副本数变化不改变 Pod template,因此通常不产生新的 revision。

rollout restart 一定会拉新镜像#

不一定。

是否拉取镜像取决于镜像 tag、imagePullPolicy、节点缓存和运行时行为。更可靠的做法是使用明确的新 tag 或 digest。

undo 就一定安全#

不一定。

回滚只处理 Kubernetes 对象层面的模板回退。数据库 schema、外部依赖、配置变更、消息格式兼容性仍然需要应用自己保证。

小结#

可以用三句话收束:

rollout 是一次发布过程;
rolling update 是 Deployment 默认的滚动更新策略;
kubectl rollout 是观察、暂停、恢复、重启、回滚发布过程的命令集合。

排查时先问:

有没有触发 rollout?
使用的是什么 strategy?
新 ReplicaSet 是否正常变大?
旧 ReplicaSet 是否正常缩小?
新 Pod 为什么没有 Ready?

这样就能把“发布没成功”拆成更可定位的问题。

参考资料#

本文共 2545 字,创建于 Jun 28, 2026

相关标签: Kubernetes, DevOps, ByAI