A Kubernetes Pod can remain Pending while CPU usage is only 3% because the scheduler checks declared resource requests and placement rules—not cluster-wide utilization alone. For an EBS-backed Pod, the volume’s Availability Zone (AZ) is another hard boundary: the Pod must run in the same AZ as its volume. Start with the Pod’s FailedScheduling event, then follow the specific constraint it identifies.
1. Find the scheduler’s reason before changing anything
Run kubectl describe pod <pod> and inspect the Events section for FailedScheduling. The event reports why the scheduler could not place that Pod; low CPU utilization does not reveal which scheduling rule failed. Kubernetes documents resource requests and scheduling behavior in its resource management guide.
As an Amazon Associate I earn from qualifying purchases.
Read the event as a clue to the blocking filter, not as proof that the whole cluster is out of capacity. A message about insufficient CPU or memory points toward resource fit; other constraints can rule out nodes even when they have spare resources. The scheduler’s documented plugins include volume binding and zone checks, as well as volume-limit checks. See the Kubernetes scheduling plugins reference.
2. Compare requests with allocatable capacity on eligible nodes
The scheduler evaluates a Pod’s declared requests against the resources available on candidate nodes. It does not use a 3% cluster CPU reading as a substitute for that comparison. Inspect the Pod’s resource requests and each potentially eligible node’s allocatable capacity, then account for requests already assigned to those nodes. Include init-container requests when determining the Pod’s effective resource needs.
#1 Best Overall
A workload can therefore be pending despite low observed CPU if its requests do not fit on any eligible node, or if other placement rules leave only nodes without enough remaining allocatable capacity. Karpenter also reasons about Pod requests and node allocatable resources when scheduling and consolidating; see its scheduling documentation. Reducing requests is appropriate only if the declared values are higher than the workload actually needs and resource fit is the identified blocker. It will not resolve a zone mismatch or an unsatisfied hard affinity rule.
3. Check which placement rules exclude nodes
Review the Pod and cluster configuration for constraints that shrink the set of nodes it can use:
nodeSelectorand required node affinity: confirm eligible nodes have the required labels.- Taints and tolerations: confirm the Pod tolerates taints on the nodes it needs to use.
- Inter-Pod affinity and topology spread constraints: check whether existing Pod placement makes the requested placement impossible.
- Resource requirements: verify CPU, memory, and other requested resources fit on at least one node that meets the other rules.
- Volume and attachment constraints: check whether the claim’s binding, AZ, or storage limits rule out otherwise suitable nodes.
Kubernetes lists plugins such as VolumeBinding, VolumeZone, and NodeVolumeLimits; the plugin reference also identifies EBSLimits. These checks mean spare CPU elsewhere in the cluster may be irrelevant if no node satisfies the Pod’s combined requirements.
Do these 3 things before closing this tab:
1Clear out junk files and repair common Windows errors2Scan for outdated or missing drivers - takes under a minute3Repair Windows errors before they cause bigger problems4. Verify that Karpenter can provision a node in the required placement
If Karpenter is expected to add capacity, inspect the applicable NodePool and NodeClass requirements. They must permit a node that meets the Pod’s resource needs and placement constraints, and the required instance types and subnets must be available in the needed AZ. A configuration that can provision nodes in other zones does not help a Pod constrained to a particular EBS volume’s zone.
Rank #3
For EKS Auto Mode or Karpenter, AWS says the NodeClass must select subnets in each AZ where EBS-backed workloads may need nodes. Check the deployed configuration and the current Amazon EKS Data Plane best-practices guidance before assuming Karpenter can satisfy the placement.
5. Trace the PVC to its PV, StorageClass, and Availability Zone
Inspect the Pod’s PersistentVolumeClaim (PVC), the bound PersistentVolume (PV), and the StorageClass. An Amazon EBS volume is zonal, not available to Pods in every AZ. Amazon EKS states: “A Pod cannot access EBS-backed persistent volumes located in a different AZ.” That means a cluster can have abundant CPU overall and still lack a usable node in the volume’s AZ.
Rank #4
Follow the claim to its actual volume and zone rather than inferring placement from the cluster’s general node count. Then check whether the Pod’s node constraints and Karpenter’s permitted subnets allow a node in that same AZ.
6. Confirm the EBS CSI provisioner and binding mode
For dynamically provisioned EBS storage, check which provisioner the StorageClass uses and how its volume binding is configured. AWS’s standard EBS CSI examples use ebs.csi.aws.com and volumeBindingMode: WaitForFirstConsumer, allowing the consuming Pod’s scheduling to inform placement and provisioning. EKS Auto Mode uses ebs.csi.eks.amazonaws.com and does not require installation of the standard EBS CSI controller. These modes are not interchangeable assumptions; identify which configuration the cluster actually uses in the Amazon EKS EBS CSI documentation before modifying a StorageClass.
7. Use the failure signal to choose a fix
Match the remedy to the constraint reported by the scheduler. Changing requests addresses a resource-fit problem only when the requests are unnecessarily high. Expanding eligible capacity addresses a shortage only if the new node can satisfy the Pod’s labels, affinity, taint, topology, and volume requirements. For an EBS-backed Pod, that includes Karpenter being able to launch a suitable node in the volume’s AZ and the claim and StorageClass being configured for the intended placement.
Per-Pod events show individual scheduling failures. For broader EKS monitoring, CloudWatch’s scheduler_pending_pods_UNSCHEDULABLE metric counts Pods the scheduler tried and failed to place, which it retains for retry. Consult the Amazon EKS CloudWatch metrics documentation for metric details.
What this diagnosis can—and cannot—establish
The mechanisms above explain why low CPU does not guarantee a schedulable Pod, but the cause in a particular cluster depends on its event message, manifests, storage configuration, and deployed Kubernetes and Karpenter versions. Without those details, no single fix can be identified in advance. Check the versions and configuration running in the cluster when validating scheduler behavior or EKS provisioning modes.
Recommended Free Tools
Quick Recap
Product prices and availability are accurate as of the date/time indicated and are subject to change. Any price and availability information displayed on Amazon at the time of purchase will apply.




