GitOps 最佳做法

本頁面提供入門指南,協助您規劃及建構 Kubernetes 的 CI/CD GitOps 管道。GitOps 搭配 Config Sync 等工具,可提升程式碼穩定性、可讀性和自動化程度。

GitOps 是快速成長的方法,可用於大規模管理 Kubernetes 設定。視您對 CI/CD 管道的需求而定,您可以選擇多種方式來架構及組織應用程式和設定程式碼。瞭解一些 GitOps 最佳做法,即可建立穩定、井然有序且安全的架構。

本頁面適用於想在環境中實作 GitOps 的管理員、架構師和操作員。如要進一步瞭解 Cloud de Confiance by S3NS 內容中提及的常見角色和工作範例,請參閱「常見的 GKE 使用者角色和工作」。

整理存放區

設定 GitOps 架構時,請根據每個存放區中儲存的設定檔類型,分隔存放區。大致來說,您至少應考慮四種類型的存放區:

  1. 用於存放相關設定群組的套件存放區。
  2. 平台存放區,用於設定整個機群的叢集和命名空間。
  3. 應用程式設定存放區。
  4. 應用程式程式碼存放區。

使用集中式私人套件存放區

使用中央存放區存放公開或內部套件 (例如 Helm 圖表),協助團隊尋找套件。舉例來說,如果存放區結構符合邏輯或包含 readme,使用集中式私人套件存放區可協助團隊快速找到資訊。您可以使用 Artifact Registry 或 Git 存放區等服務,整理中央存放區。

舉例來說,貴組織的平台團隊可以實施政策,規定應用程式團隊只能使用中央存放區中的套件。

您可以限制存放區的寫入權限,只開放給少數工程師。機構其餘成員則可擁有讀取權限。建議您實作將套件推送至中央存放區並廣播更新的程序。

雖然管理中央存放區需要有人維護,且會為應用程式團隊增加額外程序,因此會增加一些額外負擔,但這種做法有許多好處:

  • 中央團隊可以選擇按照定義的頻率新增公開套件,避免因連線能力或上游流失而中斷。
  • 在廣泛提供套件之前,可以結合自動化和人工審查員,檢查套件是否有問題。
  • 中央存放區可讓團隊瞭解目前使用和支援的項目。舉例來說,團隊可以找到儲存在中央存放區的標準 Redis 部署作業。
  • 您可以自動變更上游套件,確保符合內部標準,例如預設值、新增標籤和容器映像檔存放區。

建立 WET 存放區

WET 是「Write Everything Twice」的縮寫,與 DRY (Don't Repeat Yourself) 相反。這兩種方法代表兩種不同的設定檔:

  • DRY 設定:單一設定檔會經過轉換動作,為不同環境填入不同值的欄位。舉例來說,您可以設定共用叢集,為不同環境填入不同區域或安全性設定。
  • WET (有時稱為「完全凍結」) 設定,每個設定檔都代表最終狀態。

雖然 WET 存放區可能會導致部分設定檔重複,但對 GitOps 工作流程有以下好處:

  • 團隊成員更容易審查變更。
  • 不需經過處理,就能查看設定檔的預期狀態。

驗證設定時,提早進行測試

如果等到 Config Sync 開始同步處理才檢查問題,可能會產生不必要的 Git 提交和冗長的意見回饋循環。在將設定套用至叢集之前,您可以使用 kpt 驗證工具函式找出許多問題。

雖然您必須在修訂程序中加入額外的工具和邏輯,但在套用設定前進行測試有以下好處:

  • 在變更要求中顯示設定變更,有助於防止錯誤進入存放區。
  • 降低共用設定問題的影響。

使用資料夾,而非分支版本

請使用資料夾 (而非分支版本) 存放設定檔的變化版本。如果是資料夾,您可以使用 tree 指令查看變化版本。使用分支版本時,您無法判斷正式版和開發分支版本之間的差異,是即將發生的設定變更,還是 prod 和 dev 環境之間的永久差異。

這種做法的主要缺點是,使用資料夾時,您無法透過變更要求將設定變更推送至相同檔案。不過,使用資料夾而非分支版本有以下好處:

  • 資料夾比分支更容易找到。
  • 許多 CLI 和 GUI 工具都可對資料夾進行差異比較,但分支版本差異比較在 Git 供應商以外較不常見。
  • 使用資料夾,可以更輕鬆地區分永久差異和未升級差異。
  • 您可以在一項變更要求中,將變更部署至多個叢集和命名空間,而分支版本則需要對不同分支版本提出多項變更要求。

盡量避免使用 ClusterSelectors

ClusterSelectors 可讓您將設定的特定部分套用至部分叢集。您可以修改要套用的資源,或為叢集新增標籤,而不必設定 RootSync 或 RepoSync 物件。雖然這是為叢集新增特徵的輕量方法,但隨著 ClusterSelectors 數量增加,要瞭解叢集的最終狀態可能會變得複雜。

Config Sync 可讓您一次同步多個 RootSync 和 RepoSync 物件,因此您可以將相關設定新增至獨立存放區,然後同步至所需叢集。這樣一來,您就能更輕鬆地瞭解叢集的最終狀態,並將叢集的設定彙整到資料夾中,而不必直接在叢集上套用這些設定決策。

避免使用 Config Sync 管理工作

在大多數情況下,工作和其他情境任務應由處理生命週期管理的服務管理。接著,您可以使用 Config Sync 管理該服務,而非工作本身。

雖然 Config Sync 可以為您套用工作,但基於下列原因,工作不適合用於 GitOps 部署作業:

  • 不可變更的欄位:許多工作欄位都無法變更。如要變更不可變動的欄位,必須刪除物件並重新建立。不過,除非您從來源移除物件,否則 Config Sync 不會刪除物件。

  • 非預期執行工作:如果您使用 Config Sync 同步處理工作,然後從叢集刪除該工作,Config Sync 會將其視為與所選狀態不一致,並重新建立工作。如果您指定工作存留時間 (TTL),Config Sync 會自動刪除工作,並自動重新建立及重新啟動工作,直到您從可靠資料來源刪除工作為止。

  • 協調問題:Config Sync 通常會在套用物件後等待物件協調。不過,工作開始執行後,就會視為已協調。這表示 Config Sync 不會等待工作完成,而是會繼續套用其他物件。不過,如果工作之後失敗,則視為協調失敗。在某些情況下,這可能會導致其他資源無法同步,並造成錯誤,直到您修正為止。在其他情況下,同步處理可能會成功,只有協調失敗。

因此,我們不建議使用 Config Sync 同步處理工作。

使用非結構化存放區

Config Sync 支援兩種存放區結構:非結構化和階層式。

建議採用非結構化方法,因為這種方法可讓您以最方便的方式整理存放區。相較之下,階層式存放區會強制執行特定結構,例如 cluster 目錄中的自訂資源定義 (CRD)。這可能會在您需要共用設定時造成問題。舉例來說,如果某個團隊發布含有 CRD 的套件,另一個需要使用該套件的團隊就必須將 CRD 移至 cluster 目錄,這會增加程序的負擔。

使用非結構化存放區,可大幅簡化共用及重複使用設定套件的程序。不過,如果沒有定義明確的存放區管理程序或指南,各團隊的存放區結構可能會有所不同,導致難以導入機群層級工具。

如要瞭解如何轉換階層式存放區,請參閱「將階層式存放區轉換為非結構化存放區」。

區分程式碼和設定存放區

擴充單一存放區時,必須為每個資料夾建立專屬建構作業。負責程式碼和叢集設定的人員,通常有不同的權限和考量。

區分程式碼和設定存放區有下列好處:

  • 避免「循環」提交。例如,提交至程式碼存放區可能會觸發 CI 要求,而該要求可能會產生映像檔,然後需要提交程式碼。
  • 所需的修訂版本數量可能會成為團隊成員貢獻的負擔。
  • 您可以為處理應用程式程式碼和叢集設定的人員,設定不同的權限。

將程式碼和設定存放區分開有下列缺點:

  • 應用程式設定與應用程式程式碼不在同一個存放區,因此較難找到。
  • 管理多個存放區可能相當耗時。

使用不同的存放區來隔離變更

擴充單一存放區時,不同資料夾需要不同權限。因此,區隔存放區可讓安全性、平台和應用程式設定之間有安全邊界。此外,建議您區隔正式環境和非正式環境存放區。

雖然管理多個存放區本身可能是一項重大工作,但在不同存放區中隔離不同類型的設定具有下列優點:

  • 在設有平台、安全性和應用程式團隊的組織中,變更和權限的頻率會有所不同。
  • 權限仍位於存放區層級。CODEOWNERS 檔案可讓組織限制寫入權限,但仍允許讀取的權限。
  • Config Sync 支援每個命名空間進行多項同步作業,可達到與從多個存放區取得檔案類似的效果。

固定套件版本

無論使用 Helm 還是 Git,都應將設定套件版本固定在某個版本,以免在未明確推出新版本的情況下,不小心向前移動。

雖然這會在更新共用設定時,為推出作業增加額外檢查,但可降低共用更新造成超出預期影響的風險。

使用 Workload Identity Federation for GKE

您可以在 GKE 叢集上啟用 Workload Identity Federation for GKE,讓 Kubernetes 工作負載以安全且可控管的方式存取 Google 服務。

雖然 GitHub 和 GitLab 等部分非Cloud de Confiance by S3NS 服務不支援 Workload Identity Federation for GKE,但由於 Workload Identity Federation for GKE 可提高安全性,並降低管理密鑰和密碼的複雜度,因此建議您盡可能使用。

後續步驟