Configure capacity buffers in custom ComputeClasses

You can improve Pod scheduling speeds during scale-up operations by using capacity buffers to keep spare capacity ready in your Google Kubernetes Engine (GKE) cluster. This document shows you how to configure capacity buffers in custom ComputeClasses, which requires less setup than creating CapacityBuffers yourself. If you need more control over a buffer, such as the size of each buffer unit, replica-based sizing, or standby buffer start and refresh times, then manually create the CapacityBuffers instead. To compare the two methods, see Ways to configure capacity buffers.

This document is intended for platform administrators and cluster operators who manage custom ComputeClasses and want to provision spare capacity for scaling workloads.

Before you read this document, make sure that you're familiar with capacity buffers and custom ComputeClasses.

Limitations

Capacity buffers in a ComputeClass have the following limitations:

  • You can't change the size of a buffer unit. GKE provisions buffers in fixed units of 2 vCPUs and 2 GiB of memory.
  • You can't set the size of a buffer based on a replica count or a percentage of a workload. You can set the size of a buffer only by setting the cpu and memory values in the spec.buffers.limits field.
  • You can't customize how standby buffers start and refresh. New standby nodes stay active for 5 minutes before GKE suspends them, and GKE refreshes suspended nodes every 24 hours.
  • You can't add buffers to individual priority rules. Buffers apply to the entire ComputeClass.
  • You can't modify the CapacityBuffers and PodTemplates that GKE creates in the gke-managed-ccc namespace, including by adding labels or annotations. To change a buffer, update the ComputeClass.
  • You can't request GPUs or TPUs in the spec.buffers.limits field of a ComputeClass. Standby buffers don't support GPUs or TPUs, whether you add them to a ComputeClass or create them yourself.
  • GKE sets the size of an active buffer in a ComputeClass by CPU and memory, not by GPU or TPU count. If a ComputeClass provisions GPU or TPU nodes, then don't add an active buffer to the ComputeClass. GKE creates a buffer PodTemplate that requests only 2 vCPUs and 2 GiB of memory and no GPUs or TPUs. As a result, Pods that select the ComputeClass without requesting GPUs or TPUs can consume the buffer capacity. To provision GPU or TPU capacity by using an active buffer, manually create a CapacityBuffer whose PodTemplate requests GPUs or TPUs.
  • You can't add buffers to ComputeClasses that use the Pod-based billing model, such as ComputeClasses that have podFamily priority rules.

If you need any of these capabilities, then create CapacityBuffers manually instead. The requirements and limitations of capacity buffers, such as the machine types that standby buffers support, also apply to buffers in a ComputeClass.

Before you begin

Before you start, make sure that you have performed the following tasks:

  • Enable the Google Kubernetes Engine API.
  • Enable Google Kubernetes Engine API
  • To use the Google Cloud CLI for this task, install and then initialize the gcloud CLI. If you previously installed the gcloud CLI, get the latest version by running the gcloud components update command. Earlier gcloud CLI versions might not support running the commands in this document.
  • Create or use a GKE cluster that runs version 1.37.1-gke.3020000 or later.
  • To use standby buffers in a Standard cluster, set the value of the nodePoolAutoCreation.enabled field to true in the ComputeClass, or enable node auto-provisioning on the cluster. In Autopilot clusters, and in Autopilot mode ComputeClasses (that have the autopilot.enabled: true setting) in Standard clusters, GKE enables node pool auto-creation automatically. Active buffers don't require either setting.
  • Ensure that the ComputeClass doesn't use podFamily priority rules.
  • Ensure that the ComputeClass doesn't set the minimumCapacity field, and review how standby buffers interact with Spot VMs and active migration. For more information, see About custom ComputeClasses.

Required roles

To get the permissions that you need to add capacity buffers to custom ComputeClasses, ask your administrator to grant you the Kubernetes Engine Developer (roles/container.developer) IAM role on your project. For more information about granting roles, see Manage access to projects, folders, and organizations.

This predefined role contains the permissions required to add capacity buffers to custom ComputeClasses. To see the exact permissions that are required, expand the Required permissions section:

Required permissions

The following permissions are required to add capacity buffers to custom ComputeClasses:

  • Connect to clusters:
    • resourcemanager.projects.get
    • container.clusters.get
    • container.clusters.list
    • container.clusters.getCredentials
  • Create, update, and view ComputeClasses:
    • container.thirdPartyObjects.create
    • container.thirdPartyObjects.update
    • container.thirdPartyObjects.get
  • View the CapacityBuffers and PodTemplates that GKE creates for buffers:
    • container.thirdPartyObjects.get
    • container.thirdPartyObjects.list
    • container.podTemplates.get
    • container.podTemplates.list

You might also be able to get these permissions with custom roles or other predefined roles.

Add buffers to a ComputeClass

To add an active buffer and a standby buffer to a ComputeClass, complete the following steps:

  1. Save the following example manifest as the buffered-compute-class.yaml file:

    apiVersion: cloud.google.com/v1
    kind: ComputeClass
    metadata:
      name: buffered-class
    spec:
      priorities:
      - machineType: n2d-standard-4
      nodePoolAutoCreation:
        enabled: true
      buffers:
      # Active buffer: 4 vCPUs / 2 vCPUs per unit = 2 units
      - provisioningStrategy: buffer.x-k8s.io/active-capacity
        limits:
          cpu: "4"
      # Standby buffer: smaller of 6 / 2 and 6Gi / 2Gi = 3 units
      - provisioningStrategy: buffer.gke.io/standby-capacity
        limits:
          cpu: "6"
          memory: 6Gi
    

    This manifest creates a buffered-class ComputeClass that has the following settings:

    • nodePoolAutoCreation.enabled: true setting: lets GKE create node pools for the ComputeClass in a Standard cluster, which standby buffers require. In Autopilot clusters, and in Autopilot mode ComputeClasses in Standard clusters, GKE enables node pool auto-creation automatically. Active buffers don't require this setting.
    • buffers field: configures two buffers for the buffered-class ComputeClass. You can add at most one buffer for each provisioning strategy, so a ComputeClass can have one active buffer and one standby buffer. Each buffer has the following fields:

      • provisioningStrategy field: the buffer type. The example configures one active buffer (buffer.x-k8s.io/active-capacity) and one standby buffer (buffer.gke.io/standby-capacity). If you omit this field, then GKE creates an active buffer.
      • limits field: the total CPU and memory for the buffer. The example provisions 4 vCPUs (2 buffer units) for the active buffer, and 6 vCPUs and 6 GiB of memory (3 buffer units) for the standby buffer.

      You can set the cpu value, the memory value, or both. GKE divides the buffer into units of 2 vCPUs and 2 GiB of memory, and creates as many units as fit within all of the values that you set. If the cpu value is less than "2" or the memory value is less than 2Gi, then the buffer is empty.

  2. Apply the manifest:

    kubectl apply -f buffered-compute-class.yaml
    

    If the command fails with an unknown field "spec.buffers" error, or if GKE ignores the buffers field, then see The ComputeClass rejects or ignores the buffers field.

  3. Verify that GKE configured the buffers:

    kubectl get computeclass buffered-class \
        -o jsonpath='{.status.conditions[?(@.type=="BuffersConfigured")]}{"\n"}'
    

    The output is similar to the following:

    {"lastTransitionTime":"2026-10-14T17:02:52Z","message":"All capacity buffers configured and ready for provisioning","observedGeneration":1,"reason":"Ready","status":"True","type":"BuffersConfigured"}
    

    Check the values of the reason and status fields in the output:

    • If the reason field is Ready and the status field is True, then GKE accepted the buffers and started to provision capacity. Buffer nodes can take several minutes to appear. On a new Autopilot cluster, the condition can take about two minutes to appear. If no buffer nodes appear after several minutes, then see Buffers are ready but GKE doesn't provision capacity.
    • If the reason field is BufferIsEmpty and the status field is False, then the cpu or memory limit is less than one buffer unit (2 vCPUs and 2 GiB of memory).
    • For all other False reasons, the message field describes the issue. For the meaning of each False reason (including BufferIsEmpty) and how to resolve it, see Check BuffersConfigured condition reasons.

    To view the CapacityBuffers that GKE created for the ComputeClass, list the CapacityBuffers in the gke-managed-ccc namespace:

    kubectl get capacitybuffers -n gke-managed-ccc \
        -l cloud.google.com/compute-class=buffered-class
    
  4. If your workloads don't already select the ComputeClass, then add a node selector to their Pod specification, as shown in the following example:

    spec:
      nodeSelector:
        cloud.google.com/compute-class: buffered-class
    

    For more information about how to select a ComputeClass in workloads, see Request ComputeClasses in workloads.

Remove buffers from a ComputeClass

When you remove a buffer from a ComputeClass, GKE deletes the corresponding CapacityBuffer. If no other buffer in the ComputeClass uses that buffer's PodTemplate, then GKE deletes the PodTemplate, too. The cluster autoscaler can then scale down the nodes that are no longer needed.

  1. In your ComputeClass manifest, delete the buffers field. To remove only one buffer, delete that buffer's entry from the buffers list instead.
  2. Apply the manifest:

    kubectl apply -f buffered-compute-class.yaml
    

What's next