# Rolling Updates: maxSurge and maxUnavailable — Kubernetes

Source: https://www.skillbyai.com/en/kubernetes/w-rollout

> Replace pods without downtime.

## Two knobs control the pace

The default **RollingUpdate** strategy replaces pods gradually. **maxSurge** is how many extra pods may exist above the desired count during the update; **maxUnavailable** is how many may be unavailable below it. Both default to 25% (surge rounded up, unavailable rounded down). `maxUnavailable: 0` with `maxSurge: 1` never reduces capacity, at the cost of a slower rollout and some extra resources. New pods only count as available once their **readiness probe** passes, which is what makes rolling updates safe.

## Simulating rollout steps, run

I ran this with Python 3. It is a simplified model of Kubernetes behaviour for learning, not the real controller code. With 10 replicas and the 25% defaults, up to 13 pods may exist and at least 8 must be available; the rollout finishes in three steps. With 4 replicas, maxSurge 1 and maxUnavailable 0, it replaces one pod at a time and never drops below 4. The model assumes new pods become ready instantly; in reality readiness probes pace each step.

```python
import math
def rolling(replicas, max_surge, max_unavailable):
    surge = math.ceil(replicas * max_surge) if isinstance(max_surge, float) else max_surge
    unavail = math.floor(replicas * max_unavailable) if isinstance(max_unavailable, float) else max_unavailable
    old, new, step = replicas, 0, 0
    print(f"replicas {replicas}, maxSurge {surge}, maxUnavailable {unavail}: at most {replicas + surge} pods, at least {replicas - unavail} available")
    while old > 0 or new < replicas:          # simplified: new pods become ready instantly
        step += 1
        start = min(replicas - new, replicas + surge - (old + new))   # new pods we may start now
        new += start
        stop = min(old, (old + new) - (replicas - unavail))           # old pods we may remove once new are ready
        old -= stop
        print(f"  step {step}: +{start} new, -{stop} old -> old {old}, new {new}")
rolling(10, 0.25, 0.25)    # the default: 25% / 25%
rolling(4, 1, 0)           # zero-downtime style: surge one, never drop below 4
```

Output:

```
replicas 10, maxSurge 3, maxUnavailable 2: at most 13 pods, at least 8 available
  step 1: +3 new, -5 old -> old 5, new 3
  step 2: +5 new, -5 old -> old 0, new 8
  step 3: +2 new, -0 old -> old 0, new 10
replicas 4, maxSurge 1, maxUnavailable 0: at most 5 pods, at least 4 available
  step 1: +1 new, -1 old -> old 3, new 1
  step 2: +1 new, -1 old -> old 2, new 2
  step 3: +1 new, -1 old -> old 1, new 3
  step 4: +1 new, -1 old -> old 0, new 4
```

## Readiness probes make rollouts safe

Without a readiness probe, Kubernetes treats a pod as ready as soon as it starts, and a broken version can replace all healthy pods.

**Quiz:** What does maxUnavailable: 0 guarantee during a rollout?

- [ ] Old pods are never removed
- [ ] The rollout is instant
- [ ] No new pods are created
- [x] Available pods never drop below the desired replica count

*Answer:* Available pods never drop below the desired replica count. Capacity is preserved; surge provides the room.
