瞭解如何在 GKE 上執行主機維護作業

在長期執行的 GKE 叢集生命週期中,基礎架構中斷會導致Google Cloud 問題,進而造成工作負載定期中斷。發生這些自動事件的原因可能是排程決策 (搶占事件)、節點更新 (包括 GKE 節點自動升級 (維護事件)),或是偵測到的問題獲得修正 (終止事件)。

本文說明 GKE 中的節點中斷情形,以及如何盡量減少 GKE 節點中斷造成的影響。

如要進一步瞭解如何監控維護通知和事件,請參閱「監控維護事件」。

本文適用於下列機器類型:

本文適用於管理基礎技術架構生命週期的平台管理員和營運人員。如要進一步瞭解我們在 Google Cloud 內容中提及的常見角色和範例工作,請參閱「常見的 GKE 使用者角色和工作」。

GKE 中的基礎架構中斷是什麼意思?

GKE 叢集會管理 GKE 節點的生命週期。這些節點是在 Compute Engine VM 上佈建,因此會定期發生下列中斷情形:

  • 修復偵測到的問題 (TerminationEvent): Google Cloud 偵測到問題並中斷叢集基礎架構時,就會發生這類事件。TerminationEvent 事件不支援正常關機。下列問題會觸發 TerminationEvent 事件:

    • 自動修復:如果節點健康狀態檢查多次失敗,GKE 就會修復節點。
    • 如果實體機器的硬體或軟體發生錯誤,導致 VM 停止運作,就會發生 HostError。
  • 維護或升級事件 (MaintenanceEvent): Google Cloud 必須中斷 VM 執行維護作業時,就會發生這類事件。下列維護工作會觸發這些事件:

    • 維護事件會在 Google Cloud 升級基礎主機時發生。
    • 節點更新 (包括節點自動升級) 會在 GKE 更新節點設定時發生,例如 GKE 版本。

    如要進一步瞭解您和 GKE 如何在叢集生命週期中管理變更,請參閱「變更類型」。

  • 排程決策回應 (PreemptionEvent):當 Google Cloud 必須先占 VM,為優先順序較高的資源提供容量時,就會發生這些事件。PreemptionEvent 事件可以是下列任一項目:

    • 驅逐:當先占或 Spot 基礎架構遭到先占,以容納優先順序較高的 VM 時,就會發生驅逐情況。
    • 重整:當 GKE 預先搶占較小的 TPU 配量,以容納較大的 TPU 配量時,就會發生重整。資料重組只會在 TPU 配量上進行。

在長期執行的 GKE 叢集生命週期中,節點可能會定期中斷工作負載。如果這些中斷事件影響到執行工作負載的 GKE 節點,GKE 就必須重新啟動執行中的工作負載和基礎節點。

為什麼不支援即時遷移的節點需要中斷管理

大多數 Compute Engine VM 的主機維護政策都設為即時遷移,因此執行中的工作負載通常不會受到干擾 (少數例外)。不過,特定類別的 VM 不支援即時遷移,包括下列機型:

  • 已連接 GPU 和 TPU 的機型。
  • H4D 機型。
  • c4a-highmem-96-metal 機型。
  • Z3 機型,且連結的 Titanium SSD 超過 18 TiB。
  • Z4D 機型,且附加的 Titanium SSD 超過 41 TiB。

舉例來說,如果 TPU 磁碟區中的 VM 發生主機事件,整個磁碟區都會中斷,然後重新排程,因為所有維護事件都是在磁碟區層級協調。因此,如果您建立的 TPU 節點有數百個 VM,所有這些 VM 都會收到相同的維護事件排程。

發生主機事件時,GKE 會終止節點及其 Pod。如果 Pod 是以較大型工作負載 (例如 Job 或 Deployment) 的一部分部署,GKE 會在受影響的節點上重新啟動 Pod。

管理維護事件

本文的其餘部分將說明如何管理 MaintenanceEvent 中斷。

在主機維護事件期間管理節點中斷情形,需要經過三個階段的工作流程:

  1. 偵測排定的主機維護作業:使用 GKE 節點標籤、中繼資料端點或記錄。
  2. 對偵測到的維護作業採取行動:如果已排定維護作業,請評估基礎架構和工作負載,並根據用途決定最佳做法。採取適當行動,例如讓系統自動處理維護事件、手動啟動主機維護,或安排維護策略。
  3. 驗證維護事件的結果:確認維護事件已正確啟動,無論是 Compute Engine 依排程啟動維護事件,還是您手動啟動,都應如此。

偵測排定的主機維護作業

如要監控及偵測即將進行的維護事件,您必須查看 GKE 和 Compute Engine 的通知。

如要進一步瞭解如何監控維護通知和事件,請參閱「監控維護事件」。

對偵測到的維護作業採取行動

如果看到叢集中一或多個節點即將進行排定維護作業的通知,請使用下列決策樹,判斷處理中斷情形的最佳方式:

  1. 自動維護:讓 Compute Engine 按照排程啟動維護事件。VM 會自動在背景即時遷移,幾乎或完全不會中斷。

    1. 如果主機 VM 支援即時遷移,建議您讓維護事件自動發生。
    2. 如果工作負載在閒置彈性節點上執行,您可以設定機會性維護,自動最佳化維護時間。這項功能只會在自然閒置時段觸發必要更新。
  2. 手動啟動主機維護事件:請評估下列問題,判斷手動處理中斷事件的最佳方式:

    1. 受影響的節點是單一或獨立 VM 嗎?

      • 是 (我執行單一或獨立 VM):
        • 如果不需要精確的時間控制,請讓 Compute Engine 依排程啟動維護事件 (預設為自動)。
        • 如要避免非預期的先占,請在方便的時間 (例如流量較低時),在個別節點上手動啟動主機維護事件。
      • 否 (我正在執行加速器節點集區):請在下一個步驟中選擇其中一個選項。
    2. 根據您的用途選擇下列其中一個選項:

      • 如果加速器集區執行耦合的 AI/機器學習訓練工作: 請實作平行策略。 將訓練狀態儲存至檢查點、正常關閉集區,並在重新啟動前同時執行主機更新和 GKE 叢集升級。

      • 如果加速器集區執行高可用性 AI/機器學習服務或推論端點:請實作輪替策略。在區域或集區界線內,以輪流批次的方式協調排定的主機維護作業和版本升級,並使用作用中副本保護 SLA。

手動啟動單一或獨立 VM 的主機維護事件

您可以根據自己的時間表,手動啟動可重新排程的維護作業,例如在活動量較低的時段。如要這麼做,請在符合下列條件時套用 cloud.google.com/perform-maintenance=true 標籤:

  • Compute Engine 會發出通知,說明排定的維護事件。
  • 基礎 Compute Engine 維護事件可重新排程。如要確認活動是否可重新安排,請在活動中繼資料中尋找 can_reschedule=TRUE 通知。如果活動無法重新安排,設定 cloud.google.com/perform-maintenance=true 標籤不會有任何效果,維護作業仍會在原定時間進行。

如果符合上述條件,請在節點集區的節點上,將節點標籤 cloud.google.com/perform-maintenance 設為 true。例如:

kubectl label nodes <node-name> cloud.google.com/perform-maintenance=true

如果您啟動維護事件,GKE 會執行下列作業:

  1. 汙染節點。
  2. 妥善逐出 Pod。
  3. 要求 Compute Engine 立即啟動維護事件,而非等待排定的時間。

確認維護事件的結果

偵測到即將進行的維護作業並決定最佳行動方案後,您可以驗證維護作業的結果。

Compute Engine 會按照排程啟動維護事件

維護事件開始時,節點可能會關閉一或多次,並在即將終止前短暫通知。在這些情況下,GKE 會盡量終止工作負載,並有條理地逐出 Pod。

預定維護作業開始

排定的維護作業開始時,Compute Engine 會更新 http://metadata.google.internal/computeMetadata/v1/instance/attributes/ 目錄中的中繼資料。Compute Engine 會依下列方式更新中繼資料標籤:

  • 將 maintenance-event 設為 TERMINATE_ON_HOST_MAINTENANCE。
  • 在 upcoming-maintenance 中,將 maintenance_status 設為 ONGOING。

無論您是手動觸發排定的主機維護事件,還是讓 GKE 自動執行,系統都會偵測並處理這類事件。

下列 GKE 系統指標會回報自上次取樣以來,GKE 節點的中斷次數 (每 60 秒取樣一次):

  • kubernetes.io/node/interruption_count

interruption_type (例如 TerminationEvent、MaintenanceEvent 或 PreemptionEvent) 和 interruption_reason (例如 HostError、Eviction 或 AutoRepair) 欄位可協助提供節點中斷的原因。

如要查看專案叢集中 TPU 節點的中斷情形和原因,請使用下列 PromQL 查詢:

  sum by (interruption_type,interruption_reason)(
    sum_over_time(
      kubernetes_io:node_interruption_count{monitored_resource="k8s_node"}[${__interval}]))

如要只查看主機維護事件,請更新查詢,篩選 interruption_reason 的 HW/SW Maintenance 值。請使用下列 PromQL 查詢:

  sum by (interruption_type,interruption_reason)(
    sum_over_time(
      kubernetes_io:node_interruption_count{monitored_resource="k8s_node", interruption_reason="HW/SW Maintenance"}[${__interval}]))

如要查看依節點集區匯總的中斷次數,請使用下列 PromQL 查詢:

  sum by (node_pool_name,interruption_type,interruption_reason)(
    sum_over_time(
      kubernetes_io:node_pool_interruption_count{monitored_resource="k8s_node_pool", interruption_reason="HW/SW Maintenance", node_pool_name=NODE_POOL_NAME }[${__interval}]))

進階設定,盡可能減少干擾

本節說明其他工具,可設定叢集和工作負載,盡量減少中斷。

啟用中斷處理功能

apiVersion: v1
kind: ConfigMap
metadata:
  name: gke-disruption-handling
  namespace: kube-system
data:
  maintenance-experience.yaml: |
    gracefulTermination: true

如要啟用中斷處理功能,請建立名為 maintenance-config.yaml 的檔案,並使用這個 ConfigMap。使用下列指令將 ConfigMap 套用至叢集:

kubectl apply -f my-configmap.yaml

設定 GKE 以妥善終止工作負載

在本節中,您將設定 GKE 管理應用程式生命週期,並盡量減少工作負載中斷情形。如未設定寬限期,寬限期預設為 30 秒。

GKE 會盡量正常終止這些 Pod,並執行您定義的終止動作,例如儲存訓練狀態。GKE 會在寬限期開始時,向 Pod 傳送 SIGTERM 信號。如果 Pod 在寬限期結束前未結束,GKE 會向 Pod 中任何容器內仍在執行的程序傳送後續 SIGKILL 信號。

如要設定正常終止期,請在 Pod 資訊清單的 spec.terminationGracePeriodSeconds 欄位中,設定終止寬限期 (秒)。舉例來說,如要將通知時間設為 10 分鐘,請在 Pod 資訊清單中將 spec.terminationGracePeriodSeconds 欄位設為 600 秒,如下所示:

    spec:
      terminationGracePeriodSeconds: 600

建議您設定足夠長的終止寬限期,讓所有進行中的工作都能在通知期限內完成。如果工作負載使用 MaxText、Pax 或 JAX 等機器學習架構,並搭配 Orbax,則工作負載可以擷取關機 SIGTERM 訊號,並啟動檢查點程序。詳情請參閱「TPU 自動檢查點」。

安全終止程序

手動啟動的維護事件開始時,Compute Engine 會更新 maintenance-event 中繼資料鍵,表示機器即將關機。GKE 開始安全終止。

以下工作流程說明 GKE 如何在節點即將關閉時,執行節點正常終止程序:

  1. 60 秒內會發生以下情況:
    1. 系統元件會將 cloud.google.com/active-node-maintenance 節點標籤設為 ONGOING,表示工作負載正在停止。
    2. GKE 會套用節點污點,防止在節點上排定新的 Pod。該污點具有 cloud.google.com/impending-node-termination:NoSchedule 鍵。由於已知會發生終止作業,因此建議您不要修改工作負載,以容許這項汙點。
  2. 維護處理常式元件會先逐出工作負載 Pod,再逐出系統 Pod (例如 kube-system),開始逐出 Pod。
  3. GKE 會將 SIGTERM 關機信號傳送至節點上執行的工作負載 Pod,提醒這些 Pod 即將關機。廣告連播可使用這項快訊完成任何進行中的工作。GKE 會盡可能正常終止這些 Pod。
  4. 驅逐作業完成後,GKE 會將 cloud.google.com/active-node-maintenance 標籤的值更新為 terminating,表示節點已準備終止。

隨後節點會終止,並分配替代節點。程序完成後,GKE 會清除標籤和污點。如要延長使用 GPU 或 TPU 的工作負載終止時間,請完成「手動啟動主機維護事件」一節中的步驟。

確認進行中的安全終止作業進度

您可以依下列正常終止事件篩選 GKE 記錄:

  • 當 VM 偵測到因節點即將終止而導致中斷 (例如 Compute Engine 主機維護事件) 時,GKE 會在停止工作負載時將 cloud.google.com/active-node-maintenance 設為 ONGOING,並在工作負載完成且節點準備終止時設為 terminating。
  • 限制排定新工作負載時,GKE 會套用 cloud.google.com/impending-node-termination:NoSchedule 汙點。

透過機會維護作業,盡量減少執行中工作負載的中斷時間

當 GKE 偵測到搭載 GPU 或 TPU 的節點處於閒置狀態時,系統會自動觸發維護作業,盡量減少執行中工作負載的中斷情形。如要啟用這項功能,請建立新的節點集區。您無法對現有節點集區啟用機會維護功能。

建立新的節點集區,並啟用機會性維護

下列指令示範如何建立已啟用機會性維護功能的節點集區:

gcloud beta container node-pools create NODE_POOL_NAME \
    --cluster CLUSTER_NAME \
    --accelerator ACCELERATOR_ARG \
    --machine-type MACHINE_TYPE \
    --num-nodes NODE_COUNT \
    --zone ZONE \
    --project=PROJECT_ID \
    --opportunistic-maintenance=node-idle-time=NODE_IDLE_TIME,min-nodes=MIN_NODES,window=WINDOW

替換下列值:

  • NODE_POOL_NAME:GKE 節點集區的名稱。
  • CLUSTER_NAME:GKE 叢集的名稱。
  • NODE_IDLE_TIME:節點在觸發維護作業前,可保持閒置 (即沒有執行消耗加速器的工作負載) 的時間長度。值代表以秒為單位的時間長度,最多 9 個小數位數,結尾為 s 字元,例如:80000s。
  • MIN_NODES:節點集區中必須可用的節點數量下限。如果維護作業會導致執行中的節點數量低於這個值 (例如 10),系統就會封鎖維護作業。
  • WINDOW:以秒為單位的時間範圍,在此期間可執行機會性維護作業。值結尾為 s 字元,舉例來說,如果值為 14 天或 1209600s,表示只能在排定維護日期前兩週執行機會維護。如果值為 28 天或 2419200s,則可在排定的維護期間內隨時執行機會性維護作業。Compute Engine 主機維護作業的時段與 GKE 維護時段不同,後者決定 GKE 叢集維護作業的執行時間,且需另外設定。

機會性維護的設定範例

請看以下範例。您有一個包含四個節點的節點集區,且機會性維護設定設為 --opportunistic-maintenance=node-idle-time=600s,window=2419200s,min-nodes=3。在此情況下,會發生下列情況:

  • node1 正在執行 GPU 工作負載。這個節點並非閒置,因此系統會略過。
  • node2 已閒置 60 秒。這個節點閒置時間不足,因此系統會略過。
  • node3 已閒置 600 秒。這個節點符合閒置要求。
  • node4 已閒置 600 秒。這個節點符合閒置要求。

node3 和 node4 都符合閒置需求。不過,只有其中一個節點會觸發機會性維護,因為 min-nodes 選項的值設為 3。

檢查節點的設定和狀態 (採用機會性維護)

執行下列指令,檢查節點是否已設定機會性維護:

kubectl describe node NODE_NAME | grep node.gke.io/opportunistic-config

將 NODE_NAME 替換為要檢查的節點名稱。

檢查以機會性維護設定的節點是否正在進行維護:

kubectl describe node NODE_NAME | grep node.gke.io/maintenance-state

如果節點是由機會性維護作業觸發,註解會顯示 maintenance-stateopportunistic-triggered 為 true。

限制

請注意,機會性維護有下列限制:

  • 這項功能僅適用於 GPU 和 TPU 節點集區。
  • 叢集自動調度資源功能會縮減閒置節點,因此機會維護與叢集自動調度資源功能不相容。
  • 如果是多主機 TPU 節點集區,min-nodes-per-pool 設定的值應為 0,因為這些節點集區是不可分割的。
  • 支援的最低 GKE 版本為 1.33.3-gke.1118000。
  • 系統只支援包含can_reschedule=TRUE 通知的預定維護作業。
  • 如要停用這項功能,請重新建立節點集區,但不要加入相關旗標。或者,您也可以使用 cloud.google.com/opportunistic-disable=true,在特定節點上停用這項功能。
  • 在極少數情況下,節點的維護作業可能需要較長時間才能完成。 使用這項功能的顧客在一段時間內,可用的節點可能會減少,最低可達 min-nodes-per-pool 設定的值。

後續步驟