Skip to main content

PodDisruptionBudget

A Kubernetes policy object that limits the number of pods of a replicated application that can be simultaneously down during voluntary disruptions like node drains, cluster upgrades, or autoscaling events, ensuring minimum availability is always maintained.

PodDisruptionBudget — Extended Technical Detail

What is a PodDisruptionBudget in Simple Terms?

When you drain a node for maintenance, Kubernetes starts evicting pods. Without a PodDisruptionBudget (PDB), it could evict ALL pods of your payments service simultaneously — causing a full outage. A PDB tells Kubernetes: "Never take down more than 1 pod at a time. Always keep at least 2 running."

Voluntary vs Involuntary Disruptions

Bash
+------------------------------------------+ +------------------------------------------+
| Voluntary Disruptions | | Involuntary Disruptions |
| (PDB PROTECTS against these) | | (PDB CANNOT protect against these) |
| | | |
| * kubectl drain node | | * Node hardware failure |
| * Cluster version upgrades | | * Out-of-memory kernel kill |
| * Node autoscaling (scale down) | | * Network partition |
| * Manual pod eviction via API | | * Cloud provider AZ outage |
+------------------------------------------+ +------------------------------------------+

How a PDB Works During a Node Drain

Bash
+------------------------------------------+
| Zerodha: 5 trading-api pods across nodes | <- minAvailable: 4 is set in PDB
+------------------------------------------+
|
v
+------------------------------------------+
| kubectl drain mumbai-worker-2 | <- Operator runs maintenance drain
+------------------------------------------+
|
v
+------------------------------------------+
| Evict pod-1 (4 remaining) ALLOWED | <- PDB check: 4 >= minAvailable(4), OK
+------------------------------------------+
|
v
+------------------------------------------+
| Evict pod-2 (3 remaining) BLOCKED | <- PDB check: 3 < minAvailable(4), DENIED
| Kubernetes waits for pod-1 to reschedule | Drain pauses here automatically
+------------------------------------------+
|
v
+------------------------------------------+
| pod-1 rescheduled on worker-3 (5 again) |
| Evict pod-2 now ALLOWED (4 remaining) | <- PDB allows eviction to resume
+------------------------------------------+

Example PodDisruptionBudget

YAML
# pdb.yaml — protect the trading API from mass evictions during drain
apiVersion: policy/v1
kind: PodDisruptionBudget
metadata:
name: trading-api-pdb
namespace: production
spec:
minAvailable: 4 # Always keep at least 4 pods running
selector:
matchLabels:
app: trading-api # Targets pods with this label

minAvailable vs maxUnavailable

◈ DIAGRAM
+---------------------------+ +---------------------------+
| minAvailable: 4 | | maxUnavailable: 1 |
| | | |
| Absolute guarantee: | | Relative disruption cap: |
| at least 4 pods must be | <------> | at most 1 pod can be down |
| Running at all times | | at any given time |
| | | |
| Good for: fixed SLA pods | | Good for: scaling apps |
| (trading, payments) | | where replica count grows |
+---------------------------+ +---------------------------+
YAML
# Alternative — cap disruptions as a percentage
spec:
maxUnavailable: "20%" # At most 20% of pods can be down simultaneously
selector:
matchLabels:
app: trading-api

Percentage-Based PDB for Auto-Scaling Services

For Hotstar-style services where replica count spikes during IPL, percentage-based PDBs scale with the deployment:

YAML
apiVersion: policy/v1
kind: PodDisruptionBudget
metadata:
name: stream-api-pdb
namespace: streaming-prod
spec:
minAvailable: "80%" # Always keep 80% of pods running regardless of replica count
selector:
matchLabels:
app: stream-api

Checking PDB Status

Bash
# List all PDBs in a namespace
kubectl get pdb -n production
# NAME MIN AVAILABLE MAX UNAVAILABLE ALLOWED DISRUPTIONS AGE
# trading-api-pdb 4 N/A 1 12d
# ALLOWED DISRUPTIONS = current replicas - minAvailable
# If this is 0, the cluster CANNOT evict any pod from this deployment right now
# Describe for full details
kubectl describe pdb trading-api-pdb -n production
# Check if a drain is being blocked by a PDB
kubectl drain mumbai-worker-2 --ignore-daemonsets --delete-emptydir-data
# If blocked, output shows: Cannot evict pod as it would violate the pod's disruption budget

Troubleshooting Common PDB Problems

Problem Symptom Fix
Node drain stuck forever drain command hangs, never completes PDB ALLOWED DISRUPTIONS is 0 — a pod is not healthy enough to allow eviction. Fix the unhealthy pod first
PDB blocks cluster upgrade Upgrade stalls on a node Check if minAvailable equals replica count — reduce minAvailable by 1 temporarily
PDB not protecting pods All pods evicted despite PDB Selector matchLabels doesn't match pod labels — verify with kubectl get pods -l app=trading-api
Disruption budget confusing value ALLOWED DISRUPTIONS shows 0 unexpectedly One or more pods in the selector are not in Running state — PDB won't allow disruptions when replicas are already below threshold
PDB set on single-replica pod Drain is permanently blocked Never set minAvailable: 1 on a Deployment with only 1 replica — scale to 2 first, then drain
Remember

PDBs only protect against voluntary disruptions — planned maintenance, node drains, cluster upgrades. They cannot prevent involuntary disruptions like a node crashing due to hardware failure or a kernel OOM kill.

Tip

Always pair a PDB with a Deployment that has replicas >= minAvailable + 1. If you set minAvailable: 5 but only have 5 replicas, ALLOWED DISRUPTIONS will be 0 and no node can ever be drained. The safe formula is: replicas = minAvailable + number_of_nodes_you_drain_at_once.

Security

A PDB with minAvailable: 1 on a payment processing pod means 99% of pods could be evicted simultaneously during a hostile API call to the eviction endpoint. Always combine PDBs with RBAC restrictions on pods/eviction for sensitive workloads.

Common Mistake

Setting minAvailable equal to the total replica count (e.g., minAvailable: 5 with 5 replicas). This sets ALLOWED DISRUPTIONS to 0 permanently — the cluster can never drain any node, blocking all future upgrades, maintenance, and autoscaler scale-downs.

Frequently Asked Questions

What counts as a 'voluntary disruption' that a PodDisruptionBudget actually protects against?

PDBs only govern voluntary disruptions initiated through the Kubernetes eviction API — node drains during maintenance, cluster autoscaler scale-downs, and `kubectl drain`. They do nothing for involuntary disruptions like a node crashing, an OOM kill, or a hardware failure, since those bypass the eviction API entirely. A PDB is a safety valve for planned operations, not a general high-availability guarantee.

What's a common way a PodDisruptionBudget accidentally blocks a node drain forever?

Setting `minAvailable` equal to the total replica count (e.g., minAvailable: 3 on a Deployment with exactly 3 replicas) means zero pods can ever be voluntarily evicted, so `kubectl drain` will hang indefinitely waiting for a disruption budget that can never be satisfied. Always set minAvailable (or maxUnavailable) below the total replica count, and make sure the Deployment actually has enough replicas to tolerate losing at least one.