設定容量緩衝區

容量緩衝區會主動管理備用叢集容量,以及預先佈建和預先設定容量的暫停狀態,藉此提升重要工作負載的回應速度和可靠性。這項功能會使用 Kubernetes CapacityBuffer CustomResourceDefinition (CRD)。使用容量緩衝區,即可在叢集中明確定義特定數量的未使用節點容量。這項預留容量有助於縮短 Pod 排程時間。

當高優先順序工作負載需要快速擴充時,新工作負載可立即使用閒置容量,不必等待節點佈建。這種做法可將延遲時間降到最低,並避免在需求突然激增時發生資源爭用。

本頁面提供設定容量緩衝區的方法:固定副本緩衝區、資源限制緩衝區和百分比緩衝區。

事前準備

開始之前,請務必先完成下列工作:

  • 啟用 Google Kubernetes Engine API。
  • 啟用 Google Kubernetes Engine API
  • 如要使用 Google Cloud CLI 執行這項工作,請安裝初始化 gcloud CLI。如果您先前已安裝 gcloud CLI,請執行 gcloud components update 指令,取得最新版本。較舊的 gcloud CLI 版本可能不支援執行本文件中的指令。
  • 建立或存取 GKE 叢集,叢集版本須為 1.35.2-gke.1842000 (適用於作用中緩衝區),以及 1.36.0-gke.2253000 以上版本 (適用於待命緩衝區)。
  • 在 Standard 叢集上啟用節點自動佈建功能。在 Autopilot 叢集中,節點自動佈建功能已啟用。節點自動佈建功能為選用功能,但建議用於作用中緩衝區,且必須用於待命緩衝區。

建立必要 Kubernetes 物件

如要設定 CapacityBuffer,您需要一個命名空間來保存所有必要物件 (CapacityBuffer 本身,以及 PodTemplate 或工作負載等其他資源)。PodTemplate 和 CapacityBuffer 必須位於相同命名空間。您可以建立命名空間或使用現有命名空間,包括 default 命名空間。

視您設定的 CapacityBuffer 類型而定,您也需要下列其中一項:

  • PodTemplate:定義單一緩衝區容量單位的資源需求。CapacityBuffer 物件中指定的設定會參照 Pod 範本。
  • 工作負載:您在 CapacityBuffer 物件中參照的現有工作負載。本指南以 Deployment 物件做為工作負載範例,但容量緩衝區支援下列任一資源類型:

    • 部署作業
    • ReplicaSet
    • StatefulSet
    • ReplicationController
    • 工作
    • 實作 scale 子資源的 CustomResourceDefinitions (CRD)。

本節提供這些物件的範例。如果您已有要設定容量緩衝區的工作負載,請繼續套用容量緩衝區

如要建立 Kubernetes 工作負載範例,請完成下列步驟:

  1. 將下列資訊清單儲存為 namespace.yaml

    apiVersion: v1
    kind: Namespace
    metadata:
      name: capacity-buffer-example
      labels:
        name: capacity-buffer-example
    

    這份資訊清單會建立名為 capacity-buffer-example 的命名空間。

  2. 選用:如要搭配自訂 ComputeClass 使用容量緩衝區,請將下列資訊清單儲存為 custom-compute-class.yaml

    apiVersion: cloud.google.com/v1
    kind: ComputeClass
    metadata:
      name: ccc-example
      namespace: capacity-buffer-example
    spec:
      # Buffers are also created according to these priorities
      priorities:
      - machineFamily: n4
      - machineFamily: n4d
      - machineFamily: c4
      - machineFamily: c4d
      nodePoolAutoCreation:
        enabled: true
    

    這份資訊清單會建立自訂 ComputeClass,定義及控管 GKE 佈建節點的運算優先順序。詳情請參閱「自訂 ComputeClass」。

  3. 將下列資訊清單儲存為 buffer-pod-template.yaml

    apiVersion: v1
    kind: PodTemplate
    metadata:
      name: buffer-unit-template
      namespace: capacity-buffer-example # the namespace must be the same namespace as the CapacityBuffer
    template:
      spec:
        terminationGracePeriodSeconds: 0
        containers:
        - name: buffer-container
          image: registry.k8s.io/pause:3.9
          resources:
            requests:
              cpu: "1"
              memory: "1Gi"
            limits:
              cpu: "1"
              memory: "1Gi"
        # Optional: Using buffers with a custom ComputeClass /
        # controls the properties of the provisioned nodes.
        nodeSelector:
          cloud.google.com/compute-class: ccc-example
    

    這個資訊清單會建立 PodTemplate,定義緩衝區容量單位的資源需求 (1 CPU 和 1Gi 記憶體)。這項設定會指定 GKE 為緩衝區佈建的容量單位大小。舉例來說,如果叢集擴大,GKE 就不會將可用資源少於 1 個 CPU 和 1Gi 的節點視為緩衝區的一部分。

  4. 將下列資訊清單儲存為 sample-workload-deployment.yaml

    apiVersion: apps/v1
    kind: Deployment
    metadata:
      name: critical-workload-ref
      namespace: capacity-buffer-example # the namespace must be the same namespace as the CapacityBuffer
    spec:
      replicas: 10
      selector:
        matchLabels:
          app: critical-workload
      template:
        metadata:
          labels:
            app: critical-workload
        spec:
          containers:
          - name: busybox
            image: busybox
            command: ["sleep", "3600"]
            resources:
              requests:
                cpu: 100m
          # Optional: Using buffers with a custom ComputeClass /
          # controls the properties of the provisioned nodes.
          nodeSelector:
            cloud.google.com/compute-class: ccc-example
    

    這份資訊清單會建立含有 10 個副本的範例部署作業,這是下一節中以百分比為準的緩衝區範例參考物件。

  5. 將資訊清單套用至叢集:

    kubectl apply -f namespace.yaml -f custom-compute-class.yaml -f buffer-pod-template.yaml -f sample-workload-deployment.yaml
    
  6. 確認 GKE 已建立物件:

    kubectl get podtemplate -n capacity-buffer-example
    kubectl get deployment critical-workload-ref -n capacity-buffer-example
    

    輸出結果會與下列內容相似:

    NAME                   AGE
    buffer-unit-template   1m
    
    NAME                    READY   UP-TO-DATE   AVAILABLE   AGE
    critical-workload-ref   10/10   10           10          1m
    

套用容量緩衝區

本節提供不同類型容量緩衝區的範例,您可以將這些緩衝區套用至工作負載。

設定固定備用資源緩衝區

使用固定副本設定 CapacityBuffer 時,系統會根據 PodTemplate 指定您需要的緩衝區單元確切數量。

如要建立具有固定副本的緩衝區,請完成下列步驟:

  1. 將下列資訊清單儲存為 cb-fixed-replicas.yaml

    apiVersion: autoscaling.x-k8s.io/v1beta1
    kind: CapacityBuffer
    metadata:
      name: fixed-replica-buffer
      namespace: NAMESPACE
    spec:
      podTemplateRef:
        name: POD_TEMPLATE
      replicas: 3
      provisioningStrategy: "STRATEGY"
    

    更改下列內容:

    • NAMESPACE:命名空間的名稱,例如 capacity-buffer-example
    • POD_TEMPLATE:定義資源需求的 PodTemplate,例如 buffer-unit-template
    • STRATEGY:佈建策略,可為 "buffer.x-k8s.io/active-capacity" (預設) 或 "buffer.gke.io/standby-capacity"

    這份資訊清單會建立 CapacityBuffer 資源,參照 PodTemplate 要求特定數量的緩衝區單元。

  2. 套用資訊清單:

    kubectl apply -f cb-fixed-replicas.yaml
    
  3. 確認 GKE 已套用容量緩衝區:

    kubectl get capacitybuffer fixed-replica-buffer -n NAMESPACE
    

    狀態中的 replicas 欄位應顯示 3,這會反映您在資訊清單中定義的備用資源數量。STATUS 欄位應顯示 ReadyForProvisioning

設定資源限制緩衝區

您可以根據 PodTemplate 大小,使用 limits 欄位定義緩衝區應耗用的資源量上限。

如要建立資源限制緩衝區,請完成下列步驟:

  1. 將下列資訊清單儲存為 cb-resource-limits.yaml

    apiVersion: autoscaling.x-k8s.io/v1beta1
    kind: CapacityBuffer
    metadata:
      name: resource-limit-buffer
      namespace: NAMESPACE
    spec:
      podTemplateRef:
        name: POD_TEMPLATE
      limits:
        cpu: "5"
        memory: "5Gi"
      provisioningStrategy: "STRATEGY"
    

    更改下列內容:

    • NAMESPACE:命名空間的名稱,例如 capacity-buffer-example
    • POD_TEMPLATE:定義資源需求的 PodTemplate,例如 buffer-unit-template
    • STRATEGY:佈建策略,可為 "buffer.x-k8s.io/active-capacity" (預設) 或 "buffer.gke.io/standby-capacity"

    這份資訊清單會建立 CapacityBuffer 資源,總限制為 5 個 CPU 和 5 GiB 記憶體。如果您使用上一個步驟中的 PodTemplate 範例,請將每個單位定義為 1 CPU 和 1Gi 記憶體,這應該會產生 5 個緩衝區單位。

  2. 套用資訊清單:

    kubectl apply -f cb-resource-limits.yaml
    
  3. 確認 GKE 已套用容量緩衝區:

    kubectl get capacitybuffer resource-limit-buffer -n NAMESPACE
    

    檢查 CapacityBuffer 狀態。replicas 欄位應顯示從您定義的限制衍生而來的值。如果您使用上一節的 PodTemplate 範例,應該會看到 5 個緩衝區單元,因為這是符合定義上限的單元數量上限。

設定以百分比為準的緩衝區

設定百分比緩衝區時,系統會根據現有可擴充工作負載的百分比,動態調整緩衝區大小。百分比容量緩衝區僅適用於實作規模子資源的 Kubernetes 可調度物件,例如 Deployment、StatefulSet、ReplicaSet 或 Job。您無法為 Pod 範本定義百分比緩衝區,因為這些範本沒有 replicas 欄位。

一般而言,我們建議您從固定副本或資源限制策略著手,而非以百分比為準的緩衝區。如果工作負載縮減至低於一定數量或零,以百分比為準的緩衝區對突然擴增的反應較慢,因為安全邊際會與有效 Pod 成比例縮減。這類建議主要適用於不會縮減至極低副本數的大規模部署作業。

如要建立以百分比為準的緩衝區,請完成下列步驟:

  1. 將下列資訊清單儲存為 cb-percentage-based.yaml

    apiVersion: autoscaling.x-k8s.io/v1beta1
    kind: CapacityBuffer
    metadata:
      name: percentage-buffer
      namespace: NAMESPACE
    spec:
      scalableRef:
        apiGroup: apps
        kind: Deployment
        name: SCALABLE_RESOURCE_NAME
      percentage: 20
      provisioningStrategy: "STRATEGY"
    

    更改下列內容:

    • NAMESPACE:命名空間名稱。
    • SCALABLE_RESOURCE_NAME:可擴充資源的名稱,例如 critical-workload-ref
    • STRATEGY:佈建策略,可為 "buffer.x-k8s.io/active-capacity" (預設) 或 "buffer.gke.io/standby-capacity"

    這份資訊清單會建立 CapacityBuffer 資源,要求緩衝區大小相當於參照資源副本的 20%。如果您使用上一節的「部署」範例,副本值會設為 10

  2. 套用資訊清單:

    kubectl apply -f cb-percentage-based.yaml
    
  3. 確認 GKE 已套用容量緩衝區:

    kubectl get capacitybuffer percentage-buffer -n NAMESPACE
    

    檢查 CapacityBuffer 狀態。「replicas」欄位應顯示百分比計算值。如果您使用上一節的 Deployment 範例,應該會看到 2 緩衝區單元,這是 Deployment 中定義的 10 個副本的 20%。

  4. 手動將 Deployment 資源調度至 20 個副本,測試動態調度功能:

    kubectl scale deployment critical-workload-ref -n NAMESPACE --replicas=20
    

    CapacityBuffer 控制器會做出反應,並自動將緩衝區調度至 4 個副本。

自訂待機緩衝區行為

您可以使用註解,自訂待機緩衝區的啟動和重新整理方式。 將這些註解新增至 CapacityBuffer 資源的 metadata.annotations 欄位:

  • buffer.gke.io/standby-capacity-init-time:節點在建立後到暫停前保持活動狀態的時間長度。格式為時間長度字串 (例如 5m1h)。預設值為 5m
  • buffer.gke.io/standby-capacity-refresh-frequency:暫停節點的重新整理頻率。預設值為 24h

以下範例顯示含有這些選用欄位的資訊清單,可自訂待命緩衝區的行為:

apiVersion: autoscaling.x-k8s.io/v1beta1
kind: CapacityBuffer
metadata:
  name: customized-standby-buffer
  namespace: my-namespace
  annotations:
    buffer.gke.io/standby-capacity-init-time: "15m"
    buffer.gke.io/standby-capacity-refresh-frequency: "12h"
spec:
  podTemplateRef:
    name: buffer-unit-template
  replicas: 3
  provisioningStrategy: "buffer.gke.io/standby-capacity"

在待命緩衝區預先載入圖片

如要加快待命節點恢復運作時的工作負載啟動時間,可以使用 DaemonSet 預先載入容器映像檔。DaemonSet 會在節點暫停前的啟動期間執行。

如要使用 DaemonSet 預先載入映像檔,請完成下列步驟:

  1. 將下列資訊清單儲存為 image-puller-daemonset.yaml

    apiVersion: apps/v1
    kind: DaemonSet
    metadata:
      name: image-prefetch-daemonset
      namespace: NAMESPACE
    spec:
      selector:
        matchLabels:
          name: image-prefetch
      template:
        metadata:
          labels:
            name: image-prefetch
        spec:
          tolerations:
          - key: "buffer.gke.io/standby-node-suspended"
            operator: "Exists"
          initContainers:
          - name: image-puller
            image: IMAGE_NAME
            command: ["sh", "-c", "true"]
          containers:
          - name: pause
            image: registry.k8s.io/pause:3.9
    

    更改下列內容:

    • NAMESPACE:DaemonSet 的命名空間,例如 capacity-buffer-example
    • IMAGE_NAME:要預先載入的圖片名稱,例如 your-app-image:latest
  2. 將 DaemonSet 資訊清單套用至叢集:

    kubectl apply -f image-puller-daemonset.yaml
    
  3. 確認 DaemonSet 是否已建立:

    kubectl get daemonset image-prefetch-daemonset -n NAMESPACE
    
  4. 確認容量緩衝區已建立,且可供佈建:

    kubectl get capacitybuffer CAPACITY_BUFFER_NAME -n NAMESPACE
    

    依據換購狀態STATUS 欄位應顯示 ReadyForProvisioning

監控容量緩衝區狀態和效能

您可以使用 kubectl 指令和 Cloud Monitoring 指標,監控容量緩衝區的狀態和健康情況。

驗證 CapacityBuffer 資源狀態

如要檢查容量緩衝區的健康狀態,並確認緩衝區已準備好接收工作負載,請完成下列步驟:

  1. 取得叢集內所有容量緩衝區的狀態:

    kubectl get capacitybuffer -A
    
  2. 檢查特定緩衝區的詳細狀態、條件和事件記錄:

    kubectl describe capacitybuffer CAPACITY_BUFFER_NAME -n NAMESPACE
    

找出已暫停的待命緩衝區節點

備用緩衝區 VM 會預先佈建,但會維持暫停狀態,以協助降低成本。這些暫停的節點會顯示自訂條件,因此很容易辨識。如要稽核暫停的節點執行個體,請執行下列指令:

kubectl get nodes -o custom-columns='NAME:.metadata.name,SUSPENDED:.status.conditions[?(@.type=="Suspended")].status'

True 狀態表示待命 VM 已暫停。False<none> 狀態表示節點正在執行中。

使用 Cloud Monitoring 監控效能

如要監控容量緩衝區的效能,請在 Cloud Monitoring 中監控下列資源:

  • 反應延遲時間 (cluster_autoscaler/reaction_time_milliseconds): 追蹤叢集自動配置器根據 CapacityBuffer 待處理需求做出調整決策所需的時間。
  • 叢集自動配置器記錄:搜尋 "Capacity pod processor injecting ..." 等記錄項目,觀察緩衝區 Pod 更換事件。

移除容量緩衝區

如果工作負載不再需要容量緩衝區,請刪除 CapacityBuffer 物件。這會移除預留位置 Pod,並允許叢集自動配置器縮減節點。

kubectl delete capacitybuffer CAPACITY_BUFFER_NAME -n NAMESPACE

CAPACITY_BUFFER_NAME 替換為要刪除的 CapacityBuffer 名稱。

疑難排解

下節提供資訊,說明如何解決容量緩衝區的常見問題。

帳單模式導致容量緩衝區尚未準備就緒

如果您為使用以 Pod 為準的計費模型 (依 Pod 付費) 的工作負載建立 CapacityBuffer,系統將無法佈建容量緩衝區。

如要找出這個問題,請檢查 CapacityBuffer 狀態:

kubectl describe capacitybuffer BUFFER_NAME -n NAMESPACE

尋找類型為 ReadyForProvisioning 且狀態為 False 的條件。

如要解決這個問題,請確認 CapacityBuffer 參照的工作負載或 PodTemplate 與以節點為準的計費方式相容。

自訂可擴充資源的權限錯誤

如果您設定 CapacityBuffer 與自訂可調度物件搭配使用 (使用 scalableRef 欄位),叢集自動調度器可能缺少必要權限,而無法調度緩衝區。

如要解決這個問題,請手動建立 ClusterRoleClusterRoleBinding,授予必要權限,例如:

apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
  name: custom-scale-getter
rules:
- apiGroups: ["api.example.com"]
  resources: ["customreplicatedresources/scale"]
  verbs: ["get"]
---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  name: ca-custom-scale-getter
subjects:
- kind: User
  name: "system:cluster-autoscaler"
  namespace: kube-system
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: custom-scale-getter

如要進一步瞭解如何設定 RBAC,請參閱 Kubernetes RBAC 說明文件

後續步驟