Crisp answer: Readiness controls whether a pod receives traffic. Liveness controls whether a pod is restarted. A failing readiness probe removes the pod from the Service endpoints. A failing liveness probe kills and restarts the container.
Readiness probe:
The pod is healthy but not yet ready to serve requests — it might be warming up its cache, running database migrations, or waiting for a dependency. The readiness probe tells Kubernetes "don't send me traffic yet."
readinessProbe:
httpGet:
path: /ready
port: 8080
initialDelaySeconds: 10 # Wait 10s before first check
periodSeconds: 5 # Check every 5s
failureThreshold: 3 # Remove from endpoints after 3 failures
successThreshold: 1 # Re-add after 1 success
Effect of failing readiness: the pod IP is removed from the Service Endpoints. Traffic stops. The pod is NOT restarted. Once the probe passes again, the pod is re-added to Endpoints.
Liveness probe:
The pod is stuck — deadlock, infinite loop, corrupted state — and cannot recover without a restart. The liveness probe tells Kubernetes "I'm broken, please kill me."
livenessProbe:
httpGet:
path: /healthz
port: 8080
initialDelaySeconds: 30 # Give app time to start before liveness kicks in
periodSeconds: 10
failureThreshold: 3
timeoutSeconds: 5
Effect of failing liveness: the container is killed (SIGTERM then SIGKILL after terminationGracePeriodSeconds). Kubernetes restarts it. If it keeps failing, you get CrashLoopBackOff.
Startup probe:
For slow-starting applications. Disables liveness and readiness checks until the startup probe succeeds. Prevents liveness from killing the app during a long startup:
startupProbe:
httpGet:
path: /healthz
port: 8080
failureThreshold: 30 # 30 * 10s = 5 minutes maximum startup time
periodSeconds: 10
The three probe types:
| Type | What it does |
|---|---|
httpGet |
HTTP GET to a path — 2xx/3xx = healthy |
exec |
Runs a command in the container — exit code 0 = healthy |
tcpSocket |
TCP connect to a port — connection established = healthy |
grpc |
gRPC health check protocol |
Common mistakes:
# BAD: liveness probe on /healthz that checks DB connectivity
# If DB goes down, liveness fails, Kubernetes restarts all pods,
# which does not fix the DB but does cause an outage
livenessProbe:
httpGet:
path: /healthz # should only check the app itself, not dependencies
# BAD: readiness and liveness on the same endpoint with the same config
# Readiness should be stricter (checks dependencies), liveness should
# only check if the process is alive
# BAD: initialDelaySeconds too short for a slow-starting app
# Liveness kills the app before it has started → CrashLoopBackOff
What to say in the interview:
"Readiness and liveness answer different questions. Readiness: am I ready to receive traffic? Failing removes me from Service endpoints without restarting. Liveness: am I broken beyond self-recovery? Failing kills and restarts the container. A common mistake is putting dependency health checks in the liveness probe — if your database goes down, you don't want Kubernetes restarting all your pods, you want them to stop receiving traffic until the DB recovers. That's readiness. Liveness should only check the application process itself. The startup probe is useful for slow starters: it holds off liveness and readiness until the app signals it's up, preventing premature kills during a long initialisation."