本頁面說明如何在 Google Kubernetes Engine (GKE) 叢集中預留額外的運算容量,以便在流量高峰期間快速擴充工作負載,不必等待新節點啟動。您可以按照這些指示,持續預留運算資源,或在特定活動前預留資源。
備用容量佈建的優點
如果現有節點沒有足夠容量執行新的 Pod,GKE Autopilot 叢集和啟用節點自動佈建功能的標準叢集就會建立新節點。每個新節點的啟動時間約為 80 到 120 秒。GKE 會等到節點啟動後,才將待處理的 Pod 放置到新節點上,之後 Pod 即可啟動。在標準叢集中,您也可以手動建立新的節點集區,提供執行新 Pod 所需的額外容量。本頁面適用於使用節點自動調整機制 (例如 Autopilot 或節點自動佈建) 的叢集。
在某些情況下,您可能會希望 Pod 在擴充事件期間更快啟動。舉例來說,如果您要為熱門的即時服務多人遊戲推出新擴充內容,遊戲伺服器 Pod 的啟動速度越快,玩家在發布當天登入時的等待時間就越短。再舉一例,如果您經營電子商務平台,並打算在限定時間內舉辦快閃特賣活動,預期在特賣期間會出現流量爆增的情況。
預留容量佈建作業與 Pod 爆量功能相容,如果節點上其他 Pod 要求的容量可用且未使用,Pod 就能暫時使用這些資源。如要使用爆量功能,請將資源限制設得高於資源要求,或不要設定資源限制。詳情請參閱「在 GKE 中設定 Pod 爆量」。
GKE 中備用容量佈建的運作方式
如要佈建備用容量,可以使用 Kubernetes PriorityClasses 和預留位置 Pod。PriorityClass 可讓您告知 GKE,某些工作負載的優先順序低於其他工作負載。您可以部署使用低優先順序 PriorityClass 的預留位置 Pod,並要求預留所需的運算容量。GKE 會建立新節點,為叢集增加容量,以容納預留位置 Pod。
當生產環境工作負載擴充時,GKE 會逐一終止優先順序較低的預留位置 Pod,並在這些 Pod 的位置排定生產環境 Pod 的新副本 (使用優先順序較高的 PriorityClass)。如果您有多個優先順序較低的 Pod,且優先順序層級不同,GKE 會先逐出優先順序最低的 Pod。
容量佈建方法
視用途而定,您可以透過下列任一方式,在 GKE 叢集中佈建額外容量:
- 容量配置一致:使用 Deployment 建立特定數量的低優先順序預留位置 Pod,在叢集中持續執行。當 GKE 為了執行實際工作負載而逐出這些 Pod 時,Deployment 控制器會確保 GKE 提供更多容量,以重新建立遭逐出的低優先順序 Pod。這種方法可在多個擴大和縮減事件中提供一致的容量負擔,直到您刪除 Deployment 為止。
- 單次使用容量佈建:使用 Job 在特定時間內執行特定數量的低優先順序平行預留位置 Pod。如果時間已過,或 GKE 驅逐所有 Job 副本,預留容量就會停止提供。這個方法會提供特定期間的可用容量。
定價
在 GKE Autopilot 中,系統會針對執行中 Pod 的資源要求收費,包括您部署的低優先順序工作負載。詳情請參閱 Autopilot 定價。
在 GKE Standard 中,系統會針對 GKE 佈建的基礎 Compute Engine VM 收費,無論 Pod 是否使用該容量。詳情請參閱標準定價
事前準備
開始之前,請確認您已完成下列工作:
- 啟用 Google Kubernetes Engine API。 啟用 Google Kubernetes Engine API
- 如要使用 Google Cloud CLI 執行這項工作,請安裝並初始化 gcloud CLI。如果您先前已安裝 gcloud CLI,請執行
gcloud components update
,取得最新版本。
- 請確認您有 GKE Autopilot 叢集,或已啟用節點自動佈建功能的 GKE Standard 叢集。
- 請詳閱注意事項,確保在容量要求中選擇適當的值。
建立 PriorityClass
如要使用「容量佈建方法」一節所述的任一方法,請先建立下列 PriorityClass:
- 預設 PriorityClass:指派給任何未在 Pod 規格中明確設定不同 PriorityClass 的 Pod 的全域預設 PriorityClass。使用這個預設 PriorityClass 的 Pod 可以逐出使用較低 PriorityClass 的 Pod。
- 低優先順序 PriorityClass:非預設的 PriorityClass,在 GKE 中設為最低優先順序。系統可能會驅逐具有這個 PriorityClass 的 Pod,以執行具有較高 PriorityClass 的 Pod。
將下列資訊清單儲存為
priorityclasses.yaml
:apiVersion: scheduling.k8s.io/v1 kind: PriorityClass metadata: name: low-priority value: -10 preemptionPolicy: Never globalDefault: false description: "Low priority workloads" --- apiVersion: scheduling.k8s.io/v1 kind: PriorityClass metadata: name: default-priority value: 0 preemptionPolicy: PreemptLowerPriority globalDefault: true description: "The global default priority."
這個資訊清單包含下列欄位:
preemptionPolicy
:指定使用 PriorityClass 的 Pod 是否可以逐出優先度較低的 Pod。low-priority
PriorityClass 使用Never
,default
PriorityClass 則使用PreemptLowerPriority
。value
:使用 PriorityClass 的 Pod 優先順序。default
PriorityClass 使用0
。low-priority
PriorityClass 使用-10
。在 Autopilot 中,您可以將這個值設為小於default
PriorityClass 優先順序的任何值。在標準中,如果將這個值設為小於
-10
,使用該 PriorityClass 的 Pod 就不會觸發建立新節點,並維持在 Pending 狀態。如需優先順序適當值的相關說明,請參閱「選擇優先順序」。
globalDefault
:指定 GKE 是否要將 PriorityClass 指派給未在 Pod 規格中明確設定 PriorityClass 的 Pod。low-priority
PriorityClass 使用false
,而default
PriorityClass 使用true
。
套用資訊清單:
kubectl apply -f priorityclasses.yaml
佈建額外運算能力
以下各節的範例說明如何為單一活動或持續一段時間佈建容量。
使用 Deployment 佈建一致的容量
將下列資訊清單儲存為
capacity-res-deployment.yaml
:apiVersion: apps/v1 kind: Deployment metadata: name: capacity-res-deploy spec: replicas: 10 selector: matchLabels: app: reservation template: metadata: labels: app: reservation spec: priorityClassName: low-priority terminationGracePeriodSeconds: 0 containers: - name: ubuntu image: ubuntu command: ["sleep"] args: ["infinity"] resources: requests: cpu: 500m memory: 500Mi
這個資訊清單包含下列欄位:
spec.replicas
:請變更這個值,以符合您的需求。spec.resources.requests
:變更 CPU 和記憶體要求,以符合您的需求。請參閱「選擇容量大小」中的指引,決定適當的要求值。spec.containers.command
和spec.containers.args
:告知 Pod 保持運作,直到 GKE 逐出為止。
套用資訊清單:
kubectl apply -f capacity-res-deployment.yaml
取得 Pod 狀態:
kubectl get pods -l app=reservation
等待所有副本的狀態都變成
Running
。
使用 Job 為單一事件佈建容量
將下列資訊清單儲存為
capacity-res-job.yaml
:apiVersion: batch/v1 kind: Job metadata: name: capacity-res-job spec: parallelism: 4 backoffLimit: 0 template: spec: priorityClassName: low-priority terminationGracePeriodSeconds: 0 containers: - name: ubuntu-container image: ubuntu command: ["sleep"] args: ["36000"] resources: requests: cpu: "16" restartPolicy: Never
這個資訊清單包含下列欄位:
spec.parallelism
:變更要平行執行的 Job 數量,以預留容量。spec.backoffLimit: 0
:防止 Job 控制器重新建立遭逐出的 Job。template.spec.resources.requests
:變更 CPU 和記憶體要求,以符合您的需求。請參閱「注意事項」一節的指引,決定適當的值。template.spec.containers.command
和template.spec.containers.args
:以秒為單位,告知 Jobs 在需要額外容量的期間內保持運作。
套用資訊清單:
kubectl apply -f capacity-res-job.yaml
取得工作狀態:
kubectl get jobs
等待所有工作都顯示
Running
狀態。
測試容量佈建和驅逐
如要確認容量佈建作業是否正常運作,請按照下列步驟操作:
在終端機中,監控運算資源佈建工作負載的狀態:
如為 Deployment,請執行下列指令:
kubectl get pods --label=app=reservation -w
如要套用至 Job,請執行下列指令:
kubectl get Jobs -w
開啟新的終端機視窗,然後執行下列操作:
將下列資訊清單儲存為
test-deployment.yaml
:apiVersion: apps/v1 kind: Deployment metadata: name: helloweb labels: app: hello spec: replicas: 5 selector: matchLabels: app: hello tier: web template: metadata: labels: app: hello tier: web spec: containers: - name: hello-app image: us-docker.pkg.dev/google-samples/containers/gke/hello-app:1.0 ports: - containerPort: 8080 resources: requests: cpu: 400m memory: 400Mi
套用資訊清單:
kubectl apply -f test-deployment.yaml
在原始終端機視窗中,請注意 GKE 會終止部分容量佈建工作負載,以排定新副本的排程,類似於下列範例:
NAME READY STATUS RESTARTS AGE capacity-res-deploy-6bd9b54ffc-5p6wc 1/1 Running 0 7m25s capacity-res-deploy-6bd9b54ffc-9tjbt 1/1 Running 0 7m26s capacity-res-deploy-6bd9b54ffc-kvqr8 1/1 Running 0 2m32s capacity-res-deploy-6bd9b54ffc-n7zn4 1/1 Running 0 2m33s capacity-res-deploy-6bd9b54ffc-pgw2n 1/1 Running 0 2m32s capacity-res-deploy-6bd9b54ffc-t5t57 1/1 Running 0 2m32s capacity-res-deploy-6bd9b54ffc-v4f5f 1/1 Running 0 7m24s helloweb-85df88c986-zmk4f 0/1 Pending 0 0s helloweb-85df88c986-lllbd 0/1 Pending 0 0s helloweb-85df88c986-bw7x4 0/1 Pending 0 0s helloweb-85df88c986-gh8q8 0/1 Pending 0 0s helloweb-85df88c986-74jrl 0/1 Pending 0 0s capacity-res-deploy-6bd9b54ffc-v6dtk 1/1 Terminating 0 2m47s capacity-res-deploy-6bd9b54ffc-kvqr8 1/1 Terminating 0 2m47s capacity-res-deploy-6bd9b54ffc-pgw2n 1/1 Terminating 0 2m47s capacity-res-deploy-6bd9b54ffc-n7zn4 1/1 Terminating 0 2m48s capacity-res-deploy-6bd9b54ffc-2f8kx 1/1 Terminating 0 2m48s ... helloweb-85df88c986-lllbd 0/1 Pending 0 1s helloweb-85df88c986-gh8q8 0/1 Pending 0 1s helloweb-85df88c986-74jrl 0/1 Pending 0 1s helloweb-85df88c986-zmk4f 0/1 Pending 0 1s helloweb-85df88c986-bw7x4 0/1 Pending 0 1s helloweb-85df88c986-gh8q8 0/1 ContainerCreating 0 1s helloweb-85df88c986-zmk4f 0/1 ContainerCreating 0 1s helloweb-85df88c986-bw7x4 0/1 ContainerCreating 0 1s helloweb-85df88c986-lllbd 0/1 ContainerCreating 0 1s helloweb-85df88c986-74jrl 0/1 ContainerCreating 0 1s helloweb-85df88c986-zmk4f 1/1 Running 0 4s helloweb-85df88c986-lllbd 1/1 Running 0 4s helloweb-85df88c986-74jrl 1/1 Running 0 5s helloweb-85df88c986-gh8q8 1/1 Running 0 5s helloweb-85df88c986-bw7x4 1/1 Running 0 5s
這項輸出內容顯示,新的 Deployment 從「Pending」變更為「Running」狀態,花了五秒。
容量佈建注意事項
一致的容量佈建
- 評估您需要的預留位置 Pod 副本數量,以及每個副本中的要求大小。低優先順序副本應至少要求與最大實際工作環境工作負載相同的容量,這樣這些工作負載才能納入低優先順序工作負載保留的容量。
- 如果您大規模運作大量生產工作負載,請考慮將預留位置 Pod 的資源要求設為可提供足夠容量的值,以便執行多個生產工作負載,而不只是執行一個。
單次使用容量佈建
- 設定預留工作保留的時間長度,直到您需要額外容量為止。舉例來說,如果您希望在遊戲發布當天 (24 小時) 獲得額外容量,請將時間長度設為 86400 秒。確保佈建的容量不會超過所需時間。
- 為預留容量設定維護期間,時間長度與預留容量的時間相同。這樣可避免在節點升級期間,系統逐出低優先順序工作。預期工作負載需求量較高時,也建議設定維護期間。
- 如果您大規模運作大量實際工作環境工作負載,請考慮將預留位置 Job 的資源要求設為可提供足夠容量的值,以便執行多個實際工作環境工作負載,而不只是執行一個。
系統只會為單一縮放事件佈建容量。如果您先擴充容量並使用,然後縮減容量,該容量就不再適用於其他擴充事件。如果預期會發生多次擴大和縮減事件,請使用一致的容量預留方法,並視需要調整預留大小。舉例來說,在活動前調高 Pod 要求,活動後調低或設為零。
選擇優先順序
在 PriorityClasses 中將優先順序設為小於 0。
您可以在叢集中定義多個 PriorityClass,供需求不同的工作負載使用。舉例來說,您可以建立優先順序為 -10 的 PriorityClass,用於單次使用容量佈建,並建立優先順序為 -9 的 PriorityClass,用於一致的容量佈建。然後,您可以使用優先順序為 -9 的 PriorityClass,佈建一致的容量。當您想為特別活動增加容量時,可以部署使用優先順序為 -10 的 PriorityClass 的新 Job。GKE 會優先驅逐優先順序最低的工作負載。
您也可以使用其他 PriorityClass 執行低優先順序的非正式環境工作負載,例如容錯批次工作負載,這些工作負載的優先順序會低於正式環境工作負載,但高於預留位置 Pod。例如 -5。
選擇容量大小
將預留位置工作負載的副本計數和資源要求設為大於或等於生產環境工作負載擴充時可能需要的容量。
佈建的總容量取決於您部署的預留位置 Pod 數量,以及每個副本的資源要求。如果擴充作業需要的容量超出 GKE 為預留位置 Pod 佈建的容量,部分正式版工作負載會維持 Pending
狀態,直到 GKE 佈建更多容量為止。