Skip to content
Control Plane Labs

Karpenter vs cluster-autoscaler in 2026

Both node autoscalers are now SIG Autoscaling subprojects, and in July 2026 they started sharing an API. What actually differs, and how to choose.

Ben Ennis

Published July 27, 2026

The interesting thing about this comparison in 2026 is that it has stopped being a rivalry. Both projects are subprojects of SIG Autoscaling, both are actively released, and this month they shipped overlapping features against a shared specification. The question is no longer which one wins. It is which parts of the API are now common and which differences are load-bearing.

The architectural difference, stated precisely

The Kubernetes documentation puts it plainly. Cluster Autoscaler “adds or removes Nodes to pre-configured Node groups. Node groups generally map to some sort of cloud provider resource group,” while Karpenter “auto-provisions Nodes based on NodePool configurations provided by the cluster operator” (node autoscaling concepts).

That single difference produces most of the others. Cluster Autoscaler’s unit of work is the node group, and its FAQ requires that within a group “all machines have identical capacity and have the same set of assigned labels.” To offer a workload a choice of instance shapes, you create a node group per shape and let an expander pick between them. Karpenter’s unit of work is the NodeClaim: it reads the pending pod’s requirements, solves for an instance type, and launches it.

For a homogeneous cluster this distinction barely matters. For a cluster with GPU jobs, ARM builds, memory-heavy caches, and spot-tolerant batch, it is the whole game — the node-group approach turns into two dozen groups nobody wants to maintain.

Where each one is honest about its limits

Cluster Autoscaler documents its own scaling envelope, which is more than most projects do. The FAQ states it “should handle up to 1000 nodes running 30 pods each” and that no performance testing has been done above that. It publishes latency targets too: under 30 seconds on clusters below 100 nodes, averaging about 5 seconds, and under 60 seconds between 100 and 1000 nodes. It also warns that the pod affinity predicate is “about 3 orders of magnitude slower than for all other predicates combined,” which is a real constraint if your scheduling rules are complex.

Karpenter publishes no equivalent figures, and the widely-quoted “Karpenter provisions nodes in under a minute” numbers do not come from AWS documentation. Treat them as vendor marketing until someone publishes a methodology.

Disruption is the real differentiator

Karpenter’s disruption model is the feature people actually adopt it for, and it is more aggressive by default than most teams realise. The default consolidationPolicy is WhenEmptyOrUnderutilized with consolidateAfter: 0s, meaning Karpenter will replace a running node with a cheaper one the moment the maths works. The default disruption budget, if you define none, is a single budget of nodes: 10%, and expireAfter defaults to 720h.

Karpenter v1.14 added a third policy, Balanced, which considers whether cost savings outweigh the disruption to running pods — a middle ground between WhenEmpty and the default. Existing NodePools are unaffected unless you opt in. Most comparison content predates it.

Two details bite people. Blocking PodDisruptionBudgets and the karpenter.sh/do-not-disrupt annotation prevent voluntary disruption only; the docs are explicit that neither excludes a node from expiration, spot interruption, node repair, or manual deletion. And drift detection will replace nodes whose spec no longer matches the NodePool — correct behaviour that looks like unexplained churn the first time an AMI reference changes underneath you.

Cluster Autoscaler’s equivalent is thinner: scale down when utilisation falls below scale-down-utilization-threshold (default 0.5), evaluated on a 10-second scan interval. No drift, no cost-aware replacement, no budgets with cron windows.

The convergence nobody mentions

Here is the 2026 story. SIG Autoscaling proposed a CapacityBuffer API in the autoscaling.x-k8s.io group as a cross-autoscaler specification for provisioning headroom — replacing the pause-pod overprovisioning hack everyone has been running for years. The proposal names a second implementation in Karpenter as a graduation requirement for v1.

Karpenter delivered it. The v1.14 upgrade guide records that the release “graduates the Capacity Buffers API to v1beta1 and ships a new autoscaling.x-k8s.io_capacitybuffers CRD.” The same release added Dynamic Resource Allocation support; Cluster Autoscaler 1.36 shipped DRA partitionable-device support in the same month. Two autoscalers, one API group, overlapping feature velocity.

Google has built on the same specification: GKE’s active buffer is implemented against the OSS CapacityBuffer API, and Google’s published figures for standby buffers report P50 pod scheduling dropping from four to six minutes to single-digit seconds, at a “low single-digit percent” cost overhead. Those are the only first-party latency numbers in this space worth quoting.

How to actually choose

Run Cluster Autoscaler if your cluster is homogeneous, under a thousand nodes, already built around managed node groups, and on a cloud where Karpenter has no first-party provider. It is stable, well-understood, and its constraints are documented.

Run Karpenter if instance-shape diversity is real, if spot economics matter, or if you are on a platform that already manages it for you. On AWS, EKS Auto Mode runs Karpenter as a managed component and enforces a 21-day maximum node lifetime. On Azure, node auto-provisioning is managed Karpenter with NodePool and AKSNodeClass CRDs. Note that the GCP and Alibaba providers are third-party, not first-party cloud vendor projects.

One migration warning that still catches people: Karpenter v1.1.0 dropped v1beta1 API support entirely. Anything still on v1beta1 must go through v1.0’s conversion webhooks before upgrading further.

Frequently asked questions

Is Karpenter a CNCF project?+
Not independently. Karpenter is a subproject of Kubernetes SIG Autoscaling, alongside cluster-autoscaler, HPA, VPA, and addon-resizer. It has no separate sandbox, incubating, or graduated status of its own — it is CNCF-adjacent only by virtue of living under Kubernetes.
Can I run both at once?+
Technically yes, on disjoint node groups, and it is a common migration pattern — leave existing managed node groups under Cluster Autoscaler while new workloads land on Karpenter NodePools. Do not let both manage the same nodes; the consolidation logic will fight.
Why is Karpenter constantly replacing my nodes?+
Default consolidation. consolidationPolicy defaults to WhenEmptyOrUnderutilized with consolidateAfter: 0s, so it acts immediately whenever a cheaper packing exists. Set consolidateAfter to a few minutes, add disruption budgets, or try the new Balanced policy in v1.14.
Does a PodDisruptionBudget stop Karpenter from removing a node?+
Only for voluntary disruption — consolidation, drift, and emptiness. The documentation is explicit that PDBs and the karpenter.sh/do-not-disrupt annotation do not block expiration, spot interruption, node repair, or manual deletion. Use expireAfter and terminationGracePeriod deliberately.
Is cluster-autoscaler still maintained?+
Yes. It ships releases tracking each Kubernetes minor version under an n-3 support policy, and the 1.36 line added DRA support, fastpath binpacking, and new scale-up experiments. It is not in maintenance mode.

Tags: #kubernetes, #autoscaling, #karpenter, #eks