3. 滚动升级原理:Kubernetes Deployment 滚动更新策略、maxSurge 与 maxUnavailable 参数详解

滚动升级(Rolling Update)是 Kubernetes Deployment 默认的更新策略。它通过逐步替换旧 Pod 实例为新版本,实现零停机的应用发布。理解其底层机制与核心参数,是后续进行资源调优与瓶颈分析的基础。

3.1 滚动更新策略的核心机制

当修改 Deployment 的 Pod 模板(如镜像版本)并应用后,Kubernetes 会创建一个新的 ReplicaSet,并逐步扩容新 RS、缩容旧 RS。整个过程由 ReplicaSet Controller 和 Deployment Controller 协同完成。

关键原则:滚动更新保证在任何时刻,可用的 Pod 数量不低于期望值减去 maxUnavailable,且总 Pod 数量不超过期望值加上 maxSurge。

下图展示了滚动更新的典型流程:

Kubernetes Deployment 滚动更新流程 Deployment 滚动更新流程 旧 ReplicaSet (v1) 副本数: 5 新 ReplicaSet (v2) 副本数: 0 → 1 逐步替换 旧:5→4→3→2→1→0 旧 ReplicaSet (v1) 副本数: 0 新 ReplicaSet (v2) 副本数: 5 说明: 滚动更新通过逐步增加新 Pod 并减少旧 Pod 的方式,确保服务始终可用。 更新速度由 maxSurge 和 maxUnavailable 参数共同控制。

3.2 maxSurge 参数详解

maxSurge 定义了在滚动更新过程中,最多可以超出期望副本数(replicas)的 Pod 数量或百分比。它控制着新 Pod 的创建速度。

配置方式 示例值 含义(假设期望副本数=5) 影响
数值 maxSurge: 1 最多允许 5+1=6 个 Pod 同时存在 保守,每次只多创建 1 个新 Pod
百分比 maxSurge: 25% 最多允许 5 + ceil(5*25%)=7 个 Pod 按比例扩展,适合大规模集群
0 maxSurge: 0 不允许超出期望副本数 必须等旧 Pod 删除后才能创建新 Pod
实践建议:对于资源紧张或对突发流量敏感的场景,建议设置较小的 maxSurge(如 1 或 10%),避免短时间内创建过多 Pod 导致资源争抢。

3.3 maxUnavailable 参数详解

maxUnavailable 定义了在滚动更新过程中,最多允许有多少个 Pod 处于不可用状态。它控制着旧 Pod 的销毁速度。

配置方式 示例值 含义(假设期望副本数=5) 影响
数值 maxUnavailable: 1 最多允许 1 个 Pod 不可用 高可用,始终有 4 个 Pod 提供服务
百分比 maxUnavailable: 25% 最多允许 floor(5*25%)=1 个 Pod 不可用 按比例控制,保证服务容量
100% maxUnavailable: 100% 允许所有 Pod 同时不可用 快速更新,但存在停机风险
注意:maxUnavailable 和 maxSurge 不能同时为 0。如果两者都为 0,滚动更新将无法进行,因为既不能创建新 Pod,也不能删除旧 Pod。

3.4 参数组合与行为分析

两个参数共同决定了滚动更新的速度和安全性。以下是常见的组合策略:

策略类型 maxSurge maxUnavailable 行为描述 适用场景
快速更新 100% 100% 先创建所有新 Pod,再删除所有旧 Pod 开发/测试环境,可接受短暂双倍资源
滚动更新(默认) 25% 25% 逐步替换,每次最多超出/不可用 25% 生产环境通用配置
保守更新 1 0 先创建 1 个新 Pod,确认就绪后再删除 1 个旧 Pod 关键业务,要求最小化影响
零停机更新 1 0 始终保持期望副本数可用,逐个替换 高可用生产服务

3.5 实际配置示例

以下是一个完整的 Deployment YAML 配置,展示了滚动更新策略的声明方式:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: my-app
spec:
  replicas: 5
  strategy:
    type: RollingUpdate
    rollingUpdate:
      maxSurge: 1
      maxUnavailable: 0
  selector:
    matchLabels:
      app: my-app
  template:
    metadata:
      labels:
        app: my-app
    spec:
      containers:
      - name: my-app
        image: my-app:v2
        ports:
        - containerPort: 8080
        readinessProbe:
          httpGet:
            path: /health
            port: 8080
          initialDelaySeconds: 5
          periodSeconds: 10
关键点:readinessProbe(就绪探针)与滚动更新配合使用。只有当新 Pod 通过就绪检查后,才会被视为可用,从而触发旧 Pod 的缩容。这是保证滚动更新安全性的重要机制。

3.6 滚动更新过程中的状态观察

使用 kubectl rollout status 和 kubectl describe deployment 可以实时观察滚动更新的进度:

# 查看滚动更新状态
kubectl rollout status deployment/my-app

# 输出示例
Waiting for deployment "my-app" rollout to finish: 2 out of 5 new replicas have been updated...
Waiting for deployment "my-app" rollout to finish: 2 out of 5 new replicas have been updated...
Waiting for deployment "my-app" rollout to finish: 3 out of 5 new replicas have been updated...
deployment "my-app" successfully rolled out

# 查看详细事件
kubectl describe deployment my-app | grep -A 10 "Events:"

通过 kubectl get replicasets 可以同时看到新旧两个 ReplicaSet 的副本数变化:

NAME               DESIRED   CURRENT   READY   AGE
my-app-7d4f8b5c6   3         3         3       2m
my-app-9a2b3c4d5   2         2         2       10m

3.7 滚动更新与资源调优的关联

在后续章节中,我们将基于滚动更新的行为特征,分析资源瓶颈并优化 Argo CD 的同步策略。理解 maxSurge 和 maxUnavailable 的底层逻辑,是进行以下调优的前提:

  • 资源预留:根据 maxSurge 计算峰值资源需求,避免节点资源不足导致 Pod 调度失败。
  • 速度控制:通过调整参数,平衡更新速度与集群负载,防止突发流量压垮服务。
  • 健康检查:确保 readinessProbe 配置合理,避免因探针延迟导致滚动更新卡死。
  • 回滚策略:在更新失败时,利用 Deployment 的历史版本快速回滚,减少故障时间。
核心结论:滚动更新不是简单的“替换 Pod”,而是一个受 maxSurge 和 maxUnavailable 精确控制的状态机。这两个参数直接决定了更新的并发度和可用性保证,是后续资源调优工程中必须优先分析的配置项。