Dev/test EKS node groups paying on-demand rates for interruption-tolerant work
What does ZopNight detect here?
Spot capacity for dev/test node groups typically runs 60-70% below on-demand, and ZopNight derives the exact discount from live tier rates for the group's instance type rather than quoting a fixed number. Production-tagged groups never fire, and groups already on Spot are recognised and skipped.
Signal and threshold
| Field | Value |
|---|---|
| Rule IDs | RC-040 |
| Category | discount |
| Severity | low |
| Metric | none — pure configuration read |
| Source | eks_spot_nodepool.go |
Where it applies
Where the discount claim comes from
Fixed “save ~70% with Spot” figures age badly: Spot discounts vary by instance type, region, and week. This rule prices the group’s run-rate from the live on-demand rate for its instance type (rate × 730 hours × node count, since the node-group object itself carries no cost beyond the cluster’s own hourly charge; its EC2 workers do), then derives the Spot fraction from the live Spot rates AWS publishes for that same type. Missing either rate abstains: the percentage in the recommendation is computed from the same data as the dollar figure, never a hardcoded constant.
Classification does the safety work
Spot means interruptions: two minutes’ notice, then reclaim. The rule recommends it only where interruption is tolerable by classification: a dev/test environment tag or a dev/test-pattern name is required, and a production environment tag vetoes absolutely, even on a group whose name looks dev-ish. Two structural abstentions follow: groups whose capacity type already reads SPOT (checked from the authoritative field, so an already-discounted group is never told to switch again), and groups scaled to zero nodes, where a saving on nothing would be fabricated.
Check a group’s current capacity type
aws eks describe-nodegroup \ --cluster-name my-cluster --nodegroup-name my-ng \ --query 'nodegroup.[capacityType,instanceTypes,scalingConfig.desiredSize]'ON_DEMAND on a dev/test group is the candidate state this rule looks for.
Executing the switch, and the Karpenter question
The managed-node-group path: create a Spot group with the same instance types (several types, ideally, since diversity is what keeps Spot capacity available), cordon and drain the on-demand group, then delete it. But for clusters going Spot-heavy, AWS’s current recommendation is Karpenter: it provisions Spot capacity dynamically, handles interruption and rebalancing, and consolidates bin-packing in ways static node groups cannot. Managed node groups remain supported; new Spot adoption at scale mostly starts with Karpenter now.
Living with interruptions in dev
Dev/test tolerance still has edges: long-running integration tests and stateful dev databases mind a two-minute eviction. Keep those on a small on-demand group and let everything stateless ride Spot. The blended bill captures most of the discount without the flaky-test arguments.