Skip to main content
RunBook Academy

KubernetesXIII · Kubernetes QoS ClassesKubernetes QoS classes

Eviction order and QoS — node pressure and pod survival

Advanced⏱ ~16 minkubectl

What you'll learn

  • Explain the kubelet's eviction algorithm under node pressure
  • Identify the eviction signals (memory, disk, inodes, PIDs)
  • Tune eviction thresholds to match the workload
  • Reason about QoS-based eviction and its limits

Prerequisites

Verified against Kubernetes 1.34.x · kubeadm 1.34.x · kubectl 1.34.x · etcd 3.6.x · CoreDNS 1.11.x · containerd 1.7.x / 2.x · 2026-08-16

Not yet marked complete on this device.

The kubelet’s eviction algorithm is what protects nodes from running out of memory, disk, or PIDs. This lesson covers the algorithm, the eviction signals, and how to tune thresholds to match production workloads.

The eviction algorithm

flowchart TD
    Monitor[Kubelet monitors node resources] --> Threshold{Threshold crossed?}
    Threshold -- no --> Monitor
    Threshold -- yes --> Soft{Soft threshold?}
    Soft -- yes --> Grace[Wait grace period]
    Soft -- no --> Act[Act immediately]
    Grace --> Persistent{Pressure persists?}
    Persistent -- no --> Reset[Reset; no eviction]
    Persistent -- yes --> Act
    Act --> Sort[Sort Pods by QoS + usage]
    Sort --> Evict[Evict Pods until pressure relieved]
    Evict --> Monitor

The kubelet:

  1. Monitors node resources (memory, disk, inodes, imagefs, PIDs).
  2. Detects when a resource crosses an eviction threshold.
  3. For soft thresholds, waits the grace period to see if pressure resolves.
  4. Sorts Pods by QoS class and usage vs request.
  5. Evicts Pods one at a time until pressure is relieved.
  6. Repeats until resource is above threshold.

The pressure relief loop is important: the kubelet evicts the minimum number of Pods needed to bring the resource above threshold.

Eviction signals

The kubelet watches these signals:

SignalDescription
memory.availableMemory available for new allocations
nodefs.availableFilesystem space available on the node’s root disk
nodefs.inodesFreeInodes free on the root disk
imagefs.availableFilesystem space on the image filesystem (containerd/CRI-O)
imagefs.inodesFreeInodes free on the image filesystem
pid.availablePIDs available on the node
evictionHard:
  memory.available: 500Mi
  nodefs.available: 10%
  nodefs.inodesFree: 5%
  imagefs.available: 15%
  pid.available: 10%

The eviction order: QoS first

Within the eviction loop, Pods are sorted by:

  1. QoS class: BestEffort first, Burstable second, Guaranteed last.
  2. Within Burstable: Pods with the highest usage / request ratio are evicted first.
  3. Within Guaranteed: same logic, but Guaranteed Pods are evicted last overall.
flowchart TD
    Sort[Sort Pods] --> Q1{QoS?}
    Q1 -- BestEffort --> S1[Sort by absolute usage descending]
    Q1 -- Burstable --> S2[Sort by usage/request ratio descending]
    Q1 -- Guaranteed --> S3[Sort by usage/request ratio descending]
    S1 --> Evict[Evict in order]
    S2 --> Evict
    S3 --> Evict

For a node with 30% memory pressure:

  • All BestEffort Pods are evicted first (regardless of usage).
  • Then Burstable Pods with the highest usage-vs-request ratio.
  • If still under pressure, Guaranteed Pods with the highest ratio.

Hard vs soft thresholds

Two threshold types:

  • Hard (evictionHard): when the threshold is crossed, the kubelet evicts immediately. No grace period.
  • Soft (evictionSoft): when the threshold is crossed, the kubelet waits the grace period. If pressure resolves during the grace period, no eviction. If not, eviction proceeds.
evictionHard:
  memory.available: 500Mi

evictionSoft:
  memory.available: 1Gi

evictionSoftGracePeriod:
  memory.available: 30s

The pattern:

  • Hard threshold: the safety net. When memory is critically low, evict immediately.
  • Soft threshold: early warning. When memory is getting low, give the workload 30s to recover (e.g., a garbage collection cycle).

Tuning eviction thresholds

Production discipline:

  • Memory hard threshold: 500Mi-1Gi. Lower means earlier eviction but more Pods lost; higher means later eviction but more risk of OOMKill.
  • Memory soft threshold: 1-2Gi. Earlier warning with grace period.
  • Disk hard threshold: 10-15%. Lower means earlier eviction when emptyDir fills.
  • Imagefs hard threshold: 15-20%. The image filesystem fills up with cached image layers; eviction cleans the cache.
evictionHard:
  memory.available: 500Mi
  nodefs.available: 10%
  nodefs.inodesFree: 5%
  imagefs.available: 15%
  pid.available: 10%
evictionSoft:
  memory.available: 1Gi
  nodefs.available: 15%
evictionSoftGracePeriod:
  memory.available: 30s
  nodefs.available: 30s

Eviction signals in alerts

# Node has memory pressure condition
kube_node_status_condition{condition="MemoryPressure",status="true"} == 1

# Node has disk pressure condition
kube_node_status_condition{condition="DiskPressure",status="true"} == 1

# Pods evicted in last hour
increase(kube_pod_container_status_last_terminated_reason{reason="Evicted"}[1h])

Production discipline: alert on MemoryPressure and DiskPressure conditions; track eviction rates per node.

The kubelet eviction manager

The eviction manager runs as part of the kubelet:

  • Reads the kubelet config for thresholds.
  • Polls node resources (memory.available, nodefs.available, etc.).
  • Triggers eviction when thresholds are crossed.
  • Logs each eviction with the reason and the Pod’s QoS.
journalctl -u kubelet | grep -i evict
# I0815 12:00:00.123 ... eviction manager: must evict pod(s) to reclaim memory
# I0815 12:00:01.456 ... eviction manager: pod web-7c8 (QoS: Burstable) is evicted

The kubelet logs are the ground truth for what was evicted and why.

Production patterns

Set eviction thresholds in the kubelet config:

apiVersion: kubelet.config.k8s.io/v1beta1
kind: KubeletConfiguration
evictionHard:
  memory.available: 500Mi
  nodefs.available: 10%
evictionSoft:
  memory.available: 1Gi
evictionSoftGracePeriod:
  memory.available: 30s

Use node-level alerts:

- alert: NodeMemoryPressure
  expr: kube_node_status_condition{condition="MemoryPressure",status="true"} == 1
  for: 5m
  labels:
    severity: warning

- alert: HighEvictionRate
  expr: increase(kube_pod_container_status_last_terminated_reason{reason="Evicted"}[1h]) > 5
  labels:
    severity: warning

Investigate evicted Pods:

kubectl get pods -A --field-selector=status.reason=Evicted
# Identify Pods that were evicted; check their QoS and usage

Cross-course references

  • The Linux course part XXXVII-Linux-Resources covers cgroup OOM and node memory pressure; eviction is the cluster-level equivalent.
  • The Ansible course part XXXV-Ansible-Scripting covers service priority; QoS-based eviction is the cluster-level equivalent.
  • The Observability course part LXXXIV-Kubernetes-CapacityPlanning covers capacity planning; eviction is the response to capacity planning failures.

Quiz

Knowledge check · 4 questions

  1. Q1. Under sustained memory pressure, in what order does the kubelet evict Pods?

  2. Q2. Soft eviction thresholds give the workload a grace period to recover before eviction proceeds.

  3. Q3. A team's cluster has multiple Burstable Pods that all burst to 4Gi memory. The kubelet evicts them under memory pressure. Walk through the diagnosis and the fix.

    Cluster: 5 nodes, each with 16Gi memory. 50 Burstable Pods, each with `requests.memory: 1Gi, limits.memory: 4Gi`. Under traffic, all 50 burst to 4Gi (200Gi total demand). Nodes have 16Gi each but only 5-6Gi allocatable per node after reservations. Memory pressure triggers eviction.

  4. Q4. How do you decide on the right value for `evictionHard.memory.available`?

Passing score: 75%. Answers are checked in this browser.

Production discipline

  • Set both hard and soft eviction thresholds. Soft gives grace periods; hard is the safety net.
  • Tune thresholds to match workload peak. Memory threshold must be below the workload’s peak burst.
  • Monitor MemoryPressure and DiskPressure conditions. These signal that the kubelet has begun eviction.
  • Track eviction rates per node. High eviction rates indicate over-commitment or workload issues.
  • Plan capacity so Guaranteed Pods are not at risk. QoS is the order, not a guarantee.