GitOps指南

語言: CN / TW / HK

GitOps基於CICD和IaC,以一致的方式管理程式碼和部署,是DevOps最佳實踐之一。本文完整介紹了GitOps的理念和實踐,並介紹了Weave Cloud的GitOps模型和工具,從整體上提供了實踐GitOps的路徑和方案。原文:Guide To GitOps[1]

你是否聽說過GitOps?想不想知道什麼是GitOps?本文將介紹GitOps工作流的原則和模式,以及如何用來在生產中規模化執行Kubernetes。同時還將介紹GitOps和基礎設施即程式碼(IaC, infrastructure-as-code)配置管理工具之間的差異,當然還將展示如何將GitOps最佳實踐作為開發環境的一部分。

什麼是GitOps?

GitOps在2017年被提出作為Kubernetes叢集管理和應用交付的一種方式,利用Git作為宣告性基礎設施和應用程式的單一真實源(single source of truth)。在GitOps中,叢集中執行的軟體代理可以在執行狀態和Git發生任何差異時發出告警,Kubernetes協調器會根據情況自動更新或回滾叢集。Git作為交付流水線的中心,開發人員可以使用熟悉的工具發出pull request,從而加速和簡化Kubernetes的應用部署和操作任務。

構建雲原生應用程式的運維模型

GitOps可以概括為以下兩點:

  1. Kubernetes和其他雲原生技術的運維模型,提供了一套最佳實踐,用於統一容器化叢集和應用程式的Git部署、管理和監控。
  2. 利用開發人員的經驗管理應用程式的路徑,將端到端CICD流水線和Git工作流應用於運維和開發。

GitOps原理

要開始使用GitOps工作流管理叢集,必須具備以下條件:

1. 整個系統以宣告的方式描述。

有了Gitops, Kubernetes只是許多現代雲原生工具中的一種,這些工具都是“宣告式的”,可以被視為程式碼。宣告式意味著配置是由一組事實而不是一組指令來保證的。在Git中對應用程式的宣告進行版本化後,就有了唯一的真實來源,應用程式可以在Kubernetes上輕鬆部署和回滾。更重要的是,當發生問題時,叢集基礎設施也可以可靠的快速複製。

2. 在Git中對系統狀態進行版本控制。

通過將系統宣告儲存在版本控制系統中,並作為規範的真實來源,就有了唯一的地方派生和驅動所有東西。這種方式淡化了回滾,可以使用“Git revert”返回到之前的應用狀態。基於Git出色的安全保證,還可以使用SSH金鑰對提交進行簽名,以加強對程式碼作者和出處的安全驗證。

3. 可自動將已批准的變更應用於系統。

將宣告的狀態儲存在Git之後,下一步是允許在系統中自動應用狀態的任何變更。重要的是,不需要認證就可以對系統進行更改。在GitOps中,環境是隔離的,狀態定義位於環境之外,從而區分要做什麼和要怎麼做。

4. 軟體代理確保正確性並在狀態不一致時發出告警。

一旦系統狀態被宣告並處於版本控制之下,當實際情況與期望不匹配時,軟體代理就會發出通知。使用代理還可以確保整個系統能夠自我修復。關於自我修復,指的不僅僅是節點或pod失效(這些由kubernetes處理),而是具有更廣泛的意義,比如在人為錯誤等。在這種情況下,軟體代理充當了操作的反饋和控制迴圈。

延伸閱讀:\ Getting Started with Weave GitOps Core\ GitOps: Operations by Pull Request\ The GitOps Pipeline - Part 2\ GitOps: ‘Git Push’ all the things (The New Stack)\ The Best CI/CD Tool for Kubernetes Doesn’t Exist\ The full history of GitOps 2017-2020

GitOps的主要好處

當Git發生更改時,自動化的交付流水線將對基礎設施進行更改。但是GitOps的思想遠不止於此,GitOps使用工具來比較整個應用程式的實際生產狀態與原始碼控制下的狀態,然後當叢集狀態與期望不匹配時,就會發出通知。

通過應用GitOps最佳實踐,基礎設施和應用程式程式碼都有唯一“真實來源”,允許開發團隊提高速度並且提高系統可靠性。

延伸閱讀:\ Operate Kubernetes the GitOps Way

應用GitOps最佳實踐有很多好處:

  1. 提高生產力 整合反饋控制迴路的自動化持續部署加快了平均部署時間,幫助團隊將每天可交付的變更提升30-100倍以上,提高總體開發產出2-3倍。
  2. 增強研發體驗 推送程式碼而不是容器,開發人員可以使用Git等熟悉的工具更快管理Kubernetes的更新和特性,而無需瞭解Kubernetes的內部情況。新入職的開發人員可以在幾天內(而不是幾個月)迅速提升速度並提高生產率。
  3. 增強穩定性 當我們用Git工作流來管理叢集時,會自動獲得Kubernetes之外的所有叢集變更的審計日誌。對何人、在何時、對叢集做了什麼進行審計跟蹤,可以遵從SOC 2的要求並確保穩定性。
  4. 更高的可靠性 藉助Git的恢復/回滾和fork功能,可以獲得穩定和可重複的回滾。因為整個系統都在Git中描述,所以在崩潰後,也有唯一的真實來源來恢復,可以將恢復時間(MTTR)從幾個小時減少到幾分鐘。
  5. 一致性和標準化 由於GitOps為基礎設施、應用程式和Kubernetes附加元件的更改提供了統一的模型,因此可以在整個組織中擁有一致的端到端工作流。不僅持續整合和持續部署流水線都是由pull request驅動的,而且運維任務也完全可以通過Git反覆觸發。
  6. 強大的安全保障 Git強大的正確性和安全性保證,用於跟蹤和管理更改的強大加密技術的支援,以及為變更籤名以證明作者和來源的能力,是安全定義所需叢集狀態的關鍵。

GitOps是持續交付與雲原生的結合

GitOps基於DevOps和站點可靠性工程(Site Reliability Engineering)的想法進行構建和迭代,始於Martin Fowler在2006年發表的全面的持續整合概述[2]。

自由選擇需要的工具

作為CI/CD流水線的工作流,GitOps被描述為開發過程的聖盃[3]。因為沒有一個工具可以完成CICD流水線中需要的所有工作,所以GitOps允許自由的為不同部分選擇最佳的工具。根據特定用例,可以從開放原始碼生態系統或封閉原始碼中選擇一組工具,甚至可以組合使用。建立CICD流水線最困難的部分是將所有部分融合在一起。

無論選擇什麼工具構建交付流水線,應用Git(或任何版本控制)的GitOps最佳實踐都應該是這一流程中不可或缺的組成部分,從而更容易過渡到持續交付。不僅從技術角度看是這樣,從文化角度看也是如此。

GitOps: 在宣告性基礎設施之上的版本化CI/CD。停止編寫指令碼,開始交付。https://t.co/SgUlHgNrnY - Kelsey Hightower (@kelseyhightower) 2018年1月17日

Git支援基礎設施即程式碼(IaC)工具

Kubernetes只是許多現代雲原生工具之一,這些工具都是“宣告性的”,可以被視為程式碼。宣告性意味著配置是由一組事實來保證的,而不是一組指令,例如,“有10個redis伺服器”,而不是“啟動10個redis伺服器,然後告訴我它是否工作”。

使用宣告性工具,整個配置檔案集可以在Git中進行版本控制。通過使用Git作為真實的來源,應用程式更在Kubernetes上容易部署和回滾。更重要的是,當發生問題時,叢集基礎設施可以可靠、快速的從Git中重建。

IaC工具 vs GitOps

基礎設施即程式碼作為可按需配置伺服器的工具已經存在很長一段時間了,這些工具起源於通過程式碼控制工具維護基礎架構配置的版本、備份和可複製的概念。

但現在Kubernetes幾乎完全是宣告式的,再加上不可變的容器,可以將這些概念擴充套件到管理應用程式及其作業系統。

Git能夠管理和比較基礎設施和應用程式的當前狀態,從而通過完整的審計跟蹤進行測試、部署、回滾和前滾,這包含了GitOps哲學及其最佳實踐。由於Kubernetes幾乎完全通過宣告式配置進行管理,而且容器是不可變的,讓這一切成為可能。

我們通過Terraform和Ansible來配置伺服器,在Git中對這些配置檔案進行備份和版本控制。IaC工具及其相關配置檔案構成了GitOps工作流的核心,以便在發生問題時,能夠近乎實時的恢復叢集。可以在GitOps FAQ[4]中瞭解更多關於作為程式碼工具的基礎設施與GitOps的不同之處。

如果系統偏離了真實來源怎麼辦?

宣告性配置工具允許我們在Git中描述所需的真實狀態,但是會遇到這樣的問題:“現在真正正確的”狀態存在於真實系統中,而這可能與版本控制中描述的不同。

  • 怎麼知道真實系統是否收斂到期望狀態?
  • 當狀態不同時能收到通知嗎?
  • 遇到麻煩時,發出告警的“煤礦裡的金絲雀”是什麼?
  • 如何觸發叢集和原始碼控制之間的聚合?

這些有現成解決方案。

像Chef, Puppet和Ansible等IaC工具支援“差異提醒”等功能,幫助運維人員理解什麼時候可能需要採取行動,將真實系統“聚合”到預期的狀態(由配置指令碼定義)。最近,最佳實踐是部署不可變映象(例如容器),因此分化的可能性較小。

在“GitOps”模型中,使用Git來解決分歧以及收斂狀態,並藉助一組“diff”和“sync”工具(kubediff[5],以及terradiff和ansiblediff)來比較預期狀態和實際狀態。

基於不可變基礎設施構建GitOps

GitOps充分利用了不可變基礎設施和宣告式容器編排,為了最小化部署後變更的風險,無論是有意的還是由於“配置漂移”引起的意外,都必須維護一個可重現的、可靠的部署過程。

Git描述了整個系統的期望狀態(也就是“真實來源”)。我們基於容器實現不變性,使用不同的雲原生工具,如terrform和Ansible來自動化和管理配置。這些工具與容器和Kubernetes的宣告性特性一起幫助我們實現了當發生問題時可以完全恢復整個叢集的能力。

延伸閱讀:\ GitOps for Kubernetes: A DevOps Iteration Focused on Declarative Infrastructure\ Why we use Terraform and not Chef, Puppet, Ansible, SaltStack, or CloudFormation\ What is GitOps Really?

使用IaC工具

將GitOps原則應用於“一切”時,除了告警規則和儀表板之外,還包括機器配置、應用程式和服務,所有這些都處於原始碼控制之下。

除非通過Git,否則不需要訪問執行中的系統。任何一組更改都可以被原子的應用,並相應的加以區分。Git記錄不僅是審計日誌,也是事務日誌,可以用來回回滾到任何快照。

延伸閱讀:\ Weaveworks & AWS; How we manage Kubernetes clusters\ Provisioning and Lifecycle of a Production Ready Kubernetes Cluster\ GitOps FAQ

Weave Cloud中的持續交付和GitOps工作流

在我們的產品Weave Cloud[6]中,GitOps的核心機制整合在CI/CD工具中,關鍵部分是支援git叢集同步[7]的持續部署(CD)。

Weave Cloud是專為版本控制系統和宣告式應用程式棧設計的。團隊中的每個開發人員可能都熟悉Git,可以發出pull requet,現在他們也可以使用Git來加速和簡化Kubernetes的應用部署。

下面是一個典型的開發人員建立或更新新特性的工作流程:

  1. 一個新功能的pull request會被推送到GitHub進行稽核。
  2. 程式碼由同事稽核和批准。在修改程式碼並重新批准之後,將其合併到Git中。
  3. Git合併觸發CI和構建管道,執行一系列測試,最終構建一個新映象,並存儲到映象倉庫中。
  4. Weave Cloud “Deployment Automator”監控映象倉庫,發現新映象後,從倉庫中提取新映象並在配置倉庫中更新YAML。
  5. Weave Cloud “Deployment Synchronizer”(安裝在叢集中)檢測到叢集已過期,從配置倉庫中提取更改的manifests,將新特性部署到生產環境中。

啟用了GitOps的CICD流水線:

基於Operator模式實現的Kubernetes控制器

Weave Cloud實現了自定義控制器來監聽和同步Kubernetes叢集的部署。控制器採用Operator模式實現,Operator模式有兩個優點:首先是更安全;其次,自動化了複雜的、容易出錯的任務,比如手動更新YAML manifests。

通過使用Operator模式,代理代表叢集偵聽與自定義資源更改相關的事件,以便應用這些事件。代理負責將Git中的內容與叢集中執行的內容同步,併為團隊提供了一種實現持續部署的簡單方法。

延伸閱讀:\ Comparing Kubernetes Operator Pattern with Alternatives\ Introducing Operators: Putting Operational Knowledge into Software\ CI/CD for Kubernetes: what you need to know

Pull流水線 vs Push流水線

Push流水線

目前可用的大多數CI/CD工具都基於push模型。基於push的流水線意味著程式碼從CI系統開始,通過一系列指令碼處理,或者手工使用'kubectl'將更改推送到Kubernetes叢集。

我們不希望使用CI系統觸發部署或在命令列上手動進行部署的原因是,這可能需要在叢集外公開驗證憑據。雖然可以同時保護CI/CD指令碼和命令列,但在叢集的信任域之外工作,通常不是良好的實踐,這就是為什麼CI系統可以被認為是生產系統的攻擊媒介。

叢集外部具有讀寫許可權的典型push流水線:

在Weave Cloud中,image被拉取(pull),憑據被儲存在叢集中:

Weave Cloud Pull流水線

Weave Cloud使用pull策略,該策略由兩個關鍵元件組成: 監視映象倉庫的“Deployment Automator”和位於叢集中維護其狀態的“Deployment Synchronizer”。

Pull流水線模式的中心具有單一真實源的manifests(或配置倉庫)。開發人員將更新的程式碼推送到程式碼庫中,CI工具提取這些變更的程式碼並構建Docker映象。Weave Cloud的“Deployment Automator”發現並從映象倉庫中提取新映象,然後在配置檔案中更新YAML。然後Deployment Synchronizer檢測到叢集過期,從配置倉庫中提取更改後的manifests,並將新映象部署到叢集。

在叢集中部署Weave Cloud代理

使用叢集中的Deployment synchronizer,叢集憑據不會公開到生產環境之外。一旦在叢集中安裝了Weave Cloud代理並連線上Git倉庫,就可以通過Git pull request完成生產環境的任何變更,並且可以利用Git提供的完整的回滾以及方便的審計日誌。

延伸閱讀:\ How secure is your pipeline?

可觀察性是部署的催化劑

有了Kubernetes, GitOps可以通過pull request管理基礎設施和應用程式部署。但是GitOps工作流和可觀察性是如何協同工作的呢?

通過將GitOps工作流與實時可觀察性相結合,開發團隊可以在部署任何新特性之前做出關鍵決策。即將釋出的服務可以在釋出之前在執行的叢集中實時觀察到,這意味著可以放心部署並更快交付質量更好的特性。

可觀察性可以被視為Kubernetes持續交付[8]週期的主要驅動因素之一,描述了系統在任何給定時間的實際執行狀態。觀察執行中的系統是為了瞭解和控制它。新特性和修復被推送到git並觸發部署流水線,當準備好釋出時,可以在執行的叢集上實時觀察。此時,開發人員可以根據反饋返回到流水線的起點,或者部署映象並將其釋出到生產叢集。

GitOps是面向釋出的運維和特性模型。向客戶交付新特性的速度,一定程度上取決於團隊在這個週期中完成各個階段的速度。

同時使用GitOps工作流和可觀察性的開發人員需要回答以下問題:

  1. 如果一個變更是自動釋出的,我們怎麼知道它真的工作了?
  2. 我們如何能確定變更真的讓產品更好?
  3. 在複雜的分散式系統中,如何理解問題、診斷問題和處理事件?

通過Weave Cloud,在部署和釋出過程中整合可觀察性工作負載指示板,在承諾將部署釋出到預發或生產環境之前,可以一眼看出部署是否成功。不僅可以幫助我們更快識別問題,而且由於可觀察性工作負載指示板是實時的,並且內建在部署流程中,因此可以每天部署多次服務,並確信部署沒有重大缺陷。

延伸閱讀:\ GitOps Observability\ Monitoring Kubernetes with Prometheus

GitOps的好處

更快的開發

通過採用GitOps最佳實踐,開發人員可以使用類似Git這樣的熟悉工具更快管理Kubernetes的更新和特性。通過不斷推動功能更新,企業更加敏捷,能夠更快響應客戶需求,並在市場上更具競爭力。

更好的運維

有了GitOps,就有了完整的端到端流水線,不僅持續整合和持續部署流水線都是由pull request驅動,而且運維任務也可以通過Git完全重現。

如果使用Weave Cloud,部署到正在執行的叢集也是安全的,不會將敏感認證憑據洩露到叢集之外。

更強的安全保障

Git強大的正確性和安全性保證,用於跟蹤和管理變更的強大加密技術支援,以及簽名變更以證明作者和來源的能力,是正確和安全定義叢集所需狀態的關鍵。如果確實發生了安全漏洞,可以使用不可變和可審計的真實來源,獨立於受損的系統重新建立新系統,減少停機時間,提供更好的問題響應。

將系統構建和生產環境釋出之間的責任分離,體現了最小特權的安全原則,減少了妥協的影響並提供了更小的攻擊面。

更容易遵循規範並方便審計

由於以一種安全的方式跟蹤和記錄更改,遵循規範和審計就變得很容易了。使用像kubediff、terradiff和ansiblediff這樣的比較工具,允許將叢集狀態的可信定義與實際執行的叢集進行比較,確保被跟蹤和可審計的更改與現實相匹配。

延伸閱讀:\ Try GitOps out for yourself\ GitOps: High velocity CICD for Kubernetes\ GitOps workflows with Weave Cloud - Tutorial\ How to Boost Business Performance with GitOps: The Facts\ Multi-cloud Strategies with Kubernetes and GitOps

References:\ [1] Guide To GitOps: https://www.weave.works/technologies/gitops/ \ [2] Continuous Integration: https://martinfowler.com/articles/continuousIntegration.html \ [3] The best CI/CD tool for Kubernetes doestn't exist: https://thenewstack.io/the-best-ci-cd-tool-for-kubernetes-doesnt-exist/ \ [4] GitOps FAQ: http://www.weave.works/technologies/gitops-frequently-asked-questions \ [5] Kubediff: https://github.com/weaveworks/kubediff \ [6] Weave Cloud: https://cloud.weave.works/signup \ [7] Automated Git Cluster Synchronisation: https://github.com/fluxcd/flux/blob/master/docs/introduction.md#automated-git-cluster-synchronisation \ [8] Continuous Delivery: https://continuousdelivery.com/

你好,我是俞凡,在Motorola做過研發,現在在Mavenir做技術工作,對通訊、網路、後端架構、雲原生、DevOps、CICD、區塊鏈、AI等技術始終保持著濃厚的興趣,平時喜歡閱讀、思考,相信持續學習、終身成長,歡迎一起交流學習。\ 微信公眾號:DeepNoMind

  • END -