🔛

Karpenter の Static Capacity を使ってみる

に公開

Static Capacity とは

Karpenter は Pod の需要に合わせて Node を起動しますが、StaticCapacity を有効化すると Pod の需要に関係なく一定数の Node を維持することができます。
https://karpenter.sh/docs/concepts/nodepools/#specreplicas

2025年11月25日時点では Alpha の機能です。
https://karpenter.sh/docs/reference/settings/#feature-gates

やってみる

karpenter の Feature Gate を有効化します。

helm upgrade karpenter oci://public.ecr.aws/karpenter/karpenter \
  --version 1.8.1 \
  --namespace karpenter \
  --reuse-values \
  --set settings.featureGates.staticCapacity=true

Static Capacity の NodePool を作成します。

apiVersion: karpenter.sh/v1
kind: NodePool
metadata:
  name: static-capacity
spec:
  replicas: 10
  template:
    spec:
      requirements:
        - key: kubernetes.io/arch
          operator: In
          values: ["amd64", "arm64"]
        - key: kubernetes.io/os
          operator: In
          values: ["linux"]
        - key: karpenter.sh/capacity-type
          operator: In
          values: ["on-demand"]
        - key: karpenter.k8s.aws/instance-category
          operator: In
          values: ["c", "m", "r"]
        - key: karpenter.k8s.aws/instance-generation
          operator: Gt
          values: ["5"]
      nodeClassRef:
        group: karpenter.k8s.aws
        kind: EC2NodeClass
        name: default
      expireAfter: 720h # 30 * 24h = 720h
  limits:
    nodes: 15  # Maximum nodes during scaling/drift
  disruption:
    budgets:
    - nodes: 20%  # Disruption budget for drift replacement
    consolidateAfter: 1m

spec.replicasに設定した数の分だけ Node を起動することができます。

4 pods 起動していますが、Node 起動時に配置される Pod です。

$ kubectl get pods --all-namespaces -o wide --field-selector spec.nodeName=ip-192-168-49-235.ec2.internal

NAMESPACE          NAME                           READY   STATUS    RESTARTS   AGE     IP               NODE                             NOMINATED NODE   READINESS GATES
amazon-guardduty   aws-guardduty-agent-jk88t      1/1     Running   0          4m44s   192.168.49.235   ip-192-168-49-235.ec2.internal   <none>           <none>
kube-system        aws-node-52mnm                 2/2     Running   0          4m45s   192.168.49.235   ip-192-168-49-235.ec2.internal   <none>           <none>
kube-system        eks-pod-identity-agent-lplkr   1/1     Running   0          4m45s   192.168.49.235   ip-192-168-49-235.ec2.internal   <none>           <none>
kube-system        kube-proxy-8d4s9               1/1     Running   0          4m45s   192.168.49.235   ip-192-168-49-235.ec2.internal   <none>           <none>

以下コマンドで Node をスケールすることができます。

$ kubectl scale nodepool <name> --replicas=<count> to change replica count.

spec.limits は起動する Node の上限を指定します。

こちらにサンプルの yaml がありますが、
https://karpenter.sh/docs/concepts/nodepools/#static-nodepool

spec.template.spec.nodeClassRef や、spec.disruption.consolidateAfter など、通常の NodePool で必須の項目がないとエラーになりますので注意です。

The NodePool "static-capacity" is invalid: 
* spec.disruption.consolidateAfter: Required value
* <nil>: Invalid value: null: some validation rules were not checked because the object was invalid; correct the existing errors to complete validation

Discussion