如何使用 DevOps 構建成熟的內部開發 - VTB 經驗

DevOps 實踐工作。 當我們將版本安裝時間減少 10 倍時,我們自己也確信了這一點。 在我們在 VTB 使用的 FIS Profile 系統中,安裝現在需要 90 分鐘而不是 10 分鐘。發布構建時間從兩週縮短到兩天。 持續存在的實施缺陷的數量幾乎已降至最低。 為了擺脫“體力勞動”並消除對供應商的依賴,我們不得不拄著拐杖工作,尋找意想不到的解決方案。 剪輯下方是關於我們如何構建成熟的內部開發的詳細故事。

如何使用 DevOps 構建成熟的內部開發 - VTB 經驗
 

序言:DevOps 是一種哲學

過去一年來,我們在組織VTB內部開發和實施DevOps實踐方面做了大量的工作:

  • 我們為12個系統建立了內部開發流程;
  • 我們推出了 15 條管道,其中 XNUMX 條已投產;
  • 自動化1445個測試場景;
  • 我們成功實施了內部團隊準備的多個版本。

對於 DevSecOps 實踐的組織內部開發和實施來說,最困難的問題之一是 FIS Profile 系統,它是一個基於非關係 DBMS 的零售產品處理器。 儘管如此,我們還是能夠構建開發、啟動管道、在產品上安裝單獨的非發布包,並學習如何構建版本。 這項任務並不容易,但很有趣,並且在實施中沒有明顯的限制:這是系統 - 您需要構建內部開發。 唯一的條件是在生產環境之前使用CD。

乍一看,實現算法看起來簡單明了:

  • 我們開發初始開發專業知識,並讓代碼團隊達到可接受的質量水平,沒有嚴重缺陷;
  • 我們盡可能地融入現有流程;
  • 為了在明顯的階段之間傳輸代碼,我們切斷了一條管道並將其一端推入延續。

在此期間,所需規模的開發團隊必鬚髮展技能並將其對發布的貢獻份額增加到可接受的水平。 就這樣,你可以認為任務完成了。

看起來,這是一條達到所需結果的完全節能的路徑:這裡是DevOps,這裡是團隊的績效指標,這裡是積累的專業知識......但在實踐中,我們收到了另一個確認,即DevOps 仍然是哲學,而不是“附加到 gitlab 進程、ansible、nexus 以及列表中更靠後的位置。”

再次分析行動計劃後,我們意識到我們正在內部構建一種供應商外包。 因此,在上述算法中加入了流程再造,以及整個開發路線上的專業知識的培養,以達到在這個流程中的主導作用。 這不是最簡單的選擇,但這是思想上正確的發展之路。
 

內部開發從哪裡開始? 

我們必須使用一個遠非最友好的系統。 從架構上來說,它是一個大型的非關係型DBMS,由許多獨立的可執行對象(腳本、過程、批處理等)組成,這些對像根據需要進行調用,並根據黑盒原理工作:接收請求-發出答案。 其他值得注意的困難包括:

  • 異國語言(MUMPS);
  • 控制台界面;
  • 缺乏與流行的自動化工具和框架的集成;
  • 數據量以數十 TB 為單位;
  • 每小時超過2萬次操作的負載;
  • 重要性 - 業務關鍵。

同時,我們這邊沒有源代碼存儲庫。 完全沒有。 文檔是可用的,但所有關鍵知識和能力都在外部組織方面。
考慮到它的特性和低分佈性,我們幾乎從頭開始掌握系統的開發。 2018年XNUMX月開始:

  • 研究了代碼生成的文檔和基礎知識;
  • 我們研究了供應商提供的短期開發課程;
  • 掌握了初步的開發技能;
  • 我們為新團隊成員編寫了培訓手冊;
  • 同意將團隊納入“戰鬥”模式的工作中;
  • 解決了代碼質量控制問題;
  • 組織發展展位。

我們花了三個月的時間培養專業知識並沉浸在系統中,從2019年初開始,內部開發開始邁向光明的未來,有時會遇到困難,但充滿信心和目標明確。

存儲庫遷移和自動測試

第一個 DevOps 任務是存儲庫。 我們很快同意提供訪問權限,但有必要從當前具有一個主幹分支的 SVN 遷移到我們的目標 Git,並過渡到多個分支的模型並開發 Git Flow。 我們還有 2 個擁有自己基礎設施的團隊,以及部分供應商在國外的團隊。 我必須忍受兩個 Git 並確保同步。 在這種情況下,兩害相權取其輕。

存儲庫的遷移一再推遲,直到四月份才在前線同事的幫助下完成。 對於 Git Flow,我們決定一開始就讓事情變得簡單,並選擇了帶有修補程序、開發和發布的經典方案。 他們決定放棄master(又名prod-like)。 下面我們將解釋為什麼這個選項對我們來說是最佳選擇。 屬於供應商的外部存儲庫(兩個團隊共用)被用作工作人員。 它根據時間表與內部存儲庫同步。 現在,有了 Git 和 Gitlab,就可以實現流程自動化。

自動測試的問題出奇地容易解決——我們提供了一個現成的框架。 考慮到系統的特殊性,調用單獨的操作是業務流程的一個可以理解的部分,同時也是一個單元測試。 剩下的工作就是準備測試數據並設置調用腳本並評估結果的所需順序。 隨著基於操作執行統計、流程關鍵性和現有回歸方法形成的場景列表的填寫,自動化測試開始出現。 現在可以開始建造管道了。

它是怎樣的:自動化之前的模型

現有的實施過程模型是一個單獨的故事。 每個修改都作為單獨的增量安裝包手動傳輸。 接下來是在 Jira 中手動註冊並在環境中手動安裝。 對於單個軟件包,一切看起來都很清楚,但隨著發布的準備,事情變得更加複雜。

組裝是在單獨交付的層面上進行的,這些交付是獨立的對象。 任何更改都是新的交付。 除其他外,主要版本組合的 60-70 個包中添加了 10-15 個技術版本 - 在版本中添加或排除某些內容並反映版本外銷售變化時獲得的版本。

交付中的對象重疊,特別是在可執行代碼中,其唯一性不到一半。 已交付的代碼和剛剛計劃安裝的代碼都存在許多依賴項。 

為了獲得所需版本的代碼,必須嚴格遵循安裝順序,在此期間對像被物理重寫多次,大約10-12次。

安裝一批軟件包後,您必須手動按照說明初始化配置參數。 該版本由供應商組裝和安裝。 發布的組成幾乎直到實施的那一刻才被指定,這需要創建“解耦”包。 結果,很大一部分交付隨著“脫鉤”的尾部而從一個版本轉移到另一個版本。

現在很明顯,使用這種方法 - 在包級別組裝發布難題 - 單個主分支沒有實際意義。 生產安裝需要一個半小時到兩個小時的體力勞動。 至少在安裝程序級別指定了對象處理的順序是件好事:在輸入字段和結構的數據和過程之前輸入字段和結構。 然而,這只能在單獨的包中起作用。

這種方法的邏輯結果是不可避免的安裝缺陷,其形式包括對象的歪曲版本、不必要的代碼、缺少指令以及未考慮對象的相互影響,這些缺陷在發布後被瘋狂地消除。 

首次更新:通過提交和交付構建

自動化首先通過沿著這條路線的管道傳輸代碼:

  • 從倉庫提取成品交貨;
  • 安裝在專用環境上;
  • 運行自動測試;
  • 評估安裝結果;
  • 在測試命令一側調用以下管道。

下一個管道是在 Jira 中註冊問題,並等待命令注入到選定的測試循環中,這取決於問題實施的時間。 觸發器 - 關於已準備好交付到給定地址的信件。 當然,這是一個明顯的拐杖,但有必要從某個地方開始。 自 2019 年 XNUMX 月以來,已開始傳輸代碼並檢查我們的環境。 這個過程已經開始,剩下的就是將其變成一個合適的形式:

  • 每個修訂版運行在與安裝包匹配的單獨分支上,並合併到目標主分支中;
  • 管道啟動觸發器是通過合併請求在主分支中出現新的提交,該提交由內部團隊的維護人員關閉;
  • 存儲庫每五分鐘同步一次;
  • 使用從供應商處收到的彙編器開始安裝包的彙編。

此後,已經有檢查和傳輸代碼、啟動管道並在我們這邊組裝的現有步驟。

該選項於七月推出。 過渡的困難導致了供應商和一線人員的一些不滿,但在接下來的一個月裡,我們設法消除了所有的粗糙邊緣並改進了團隊的流程。 我們通過提交和交付進行構建。
40 月份,我們成功地使用我們的管道首次安裝了用於生產的單獨軟件包,自 XNUMX 月份以來,所有未發佈軟件包的安裝無一例外都是通過我們的 CD 工具執行的。 此外,我們成功地以比供應商更小的團隊完成了 XNUMX% 的版本組成中的內部任務 - 這絕對是成功的。 最重要的任務仍然是 - 構建和安裝版本。

最終解決方案:累積安裝包 

我們非常清楚,編寫供應商指令的腳本是馬馬虎虎的自動化,我們必須重新考慮流程本身。 解決方案就表面而言 - 從發布分支收集累積交付以及所需版本的所有對象。

我們從概念驗證開始:我們根據過去實現的內容手動組裝發布包並將其安裝在我們的環境中。 一切順利,這個概念被證明是可行的。 接下來,我們解決了編寫初始化設置腳本並將其包含在提交中的問題。 作為輪廓更新的一部分,我們準備了一個新包並在測試環境中對其進行了測試。 儘管實施團隊提出了廣泛的評論,但安裝還是成功的。 但最重要的是,我們已獲准在 XNUMX 月份的版本中進行組裝並投入生產。

只剩下一個多月的時間了,精心挑選的物資顯然暗示著時間已經不多了。 他們決定從發布分支進行構建,但為什麼要把它分開呢? 我們沒有類似產品的產品,現有的分支也不好——有很多不必要的代碼。 我們迫切需要削減類似的產品,這已經超過三千次提交。 手工組裝根本不是一種選擇。 我們草擬了一個腳本,該腳本運行生產安裝日誌並將提交收集到分支中。 從第三次開始,它就正常工作了,並且在“完成文件”之後,分支就準備好了。 

我們為安裝包編寫了自己的構建器,並在一周內完成了它。 然後我們必須從系統的核心功能修改安裝程序,因為它是開源的。 經過一系列的檢查和修改,結果算是成功了。 與此同時,版本的組成已經形成,為了正確安裝,必須將測試電路與生產電路對齊,並為此編寫了一個單獨的腳本。

當然,對於第一次安裝有很多評論,但總的來說,代碼是有效的。 大約第三次安裝後,一切開始看起來不錯。 對象的組成和版本控制是在手動模式下單獨監控的,這在現階段是相當合理的。

另一個複雜的問題是必須考慮到大量的未發布版本。 但有了類似 Prod 的分支和 Rebase,任務就變得透明了。

第一次,快速且無錯誤

我們以樂觀的態度對待發布,並在不同的電路上成功安裝了十幾次。 但實際上就在截止日期前一天,事實證明供應商尚未完成以可接受的方式準備安裝版本的工作。 如果由於某種原因我們的構建無法正常工作,發布將會中斷。 而且,通過我們的努力,這是特別不愉快的。 我們無路可退。 因此,我們考慮了替代方案,準備了行動計劃並開始安裝。

令人驚訝的是,由 800 多個對象組成的整個發布首次在短短 10 分鐘內就正確啟動。 我們花了一個小時檢查日誌尋找錯誤,但沒有發現任何錯誤。

第二天一整天,發布聊天室一片寂靜:沒有實現問題、不正確的版本或“遺留”代碼。 甚至有點尷尬。 後來也有個別意見出來,但相對於其他系統的背景和以往的經驗,其數量和優先級明顯較低。

累積的另一個效果是組裝和測試質量的提高。 由於完整版本的多次安裝,構建缺陷和部署錯誤被及時檢測到。 在完整版本配置中進行測試可以額外識別增量安裝期間未出現的對象交互中的缺陷。 這絕對是成功的,特別是考慮到我們對發布的 57% 貢獻。

結果與結論

在不到一年的時間裡,我們成功做到了:

  • 使用外來系統構建成熟的內部開發;
  • 消除對供應商的關鍵依賴;
  • 運行 CI/CD 是為了非常不友好的遺留問題;
  • 將實施流程提升到新的技術水平;
  • 顯著減少部署時間;
  • 顯著減少執行錯誤的數量;
  • 自信地宣稱自己是領先的開發專家。

當然,所描述的大部分內容看起來完全是廢話,但這些都是系統的特徵以及其中存在的流程限制。 目前,這些變化影響了 IS Profile 產品和服務(主賬戶、塑料卡、儲蓄賬戶、託管、現金貸款),但該方法可能適用於任何設定了實施 DevOps 實踐任務的 IS。 可以從許多交付中安全地複制累積模型以用於後續實施(包括非發布實施)。

來源: www.habr.com

添加評論