在 Day14 的時候,我們介紹了 Git 使用優點以及相關的生產環境,其中就有提到,當我們完成 commit & push 的時候,Git Repository 可以利用 Webhook 感知到更新,並傳送 Request 到 CI 工具,觸發 CI 工具 Checkout (拉取) 程式碼,執行編譯測試與發佈的動作。
當我們首次建立 Git,他會為我們預設 master 分支,而小型團隊可能就會在相同的 master 上進行開發,團隊可能會約定每個人先在 local commit,在完成測試後推送到 Repository 內,而每個人再推送前都要養成先 pull 的習慣;又或者會依照需求而開立分支,交由特定的人或組別去完成。
隨著專案開發的人數與需求的增加,五花八門的 Commit & Push 最終都難逃一個亂字,也因此,開始逐漸形成一套規範,用於絕大多數的開發場景,而最著名的規範 Gitflow 則是由 Vincent Driessen 所提出的 A successful Git branching model
Gitflow 是一種規範,是一種推薦的實作方法,這也意味著團隊可以依照需求去改動,而既然是規範,自然會有幾個要點,這裡逐一介紹:
master
、developer
、hotfixes
、release
、frature
組成而這五個分支會個別負責幾個功能:
Dev 分支是開發的核心,在操作上其實與 master 類似,PG 不會主動在 Dev 分支上進行開發,取而代之的是從 Dev 分支內創建一個 Feature 分支來完成需求,當 Feature 分支完成後,才合併回 Dev 內。
而 Dev 分支通常會掛上 Webhook 並執行自動化的編譯、測試、打包與部署,而部署的環境通常為 SIT,用於團隊直接操作驗證。
Feature 是從 Dev 中創建出來的分支,用於完成特定的功能開發,當完成的時候會被合併回 Dev 內。一般而言,每個 Feature 的生命週期會和每期 Sprint 一致,Product Owner 會訂定這一起的 Sprint 要完成的目標,而當期開出來的 Featrue 則是完成該目標下的功能。
而當 Featrue 無法在 Sprint 期限內完成時,Product Owner 則應該調查團隊內部是否有需要協助,或是審視 Featrue 是否包含了太多的功能。當團隊數量到達一定規模時,在同一期的 Sprint 其實可以開立多個 Featrue,藉由併行的方式完成多個功能。
Featrue 通常對應的是開發者自身的電腦,等於是在本機上完成測試後推送。
Release 則是當 Developer 分支已經完成到能夠滿足一系列的需求時,從 Developer 中開出的分支,用於做進一步的測試。在某些情況下,Release 也會對應到一個臨時的環境,如模擬壓力測試的環境。
當 Release 的測試結束後,則將他 merge 到 master 分支;若 Release 測試發現一些問題,並在上面修正後,除了 merge 到 master 外,亦會 merge 到 developer 上。
master 會放置最穩定的程式碼版本,並且是可以隨時上線的(當不幸發生問題的時候可以立即退回上一個 master 版本止血),也因此,程式碼要上到 master,必須先在其他的分支完成檢驗,然後 merge 進來,絕對不會讓 PG 在 master 上修改並 commit (因為可能會忽略驗證導致破洞越來越大)。
通常,我們會對永久分支掛上 Webhook,當分支的程式碼更新時觸發一些事件,而 master 更新可以設置為觸發自動將新的版本部署到正式生產環境(Production)上,其不一定會編譯與打包,而是拉取 Image 以及對應的部署配置檔 & 環境配置檔進行部署。
當 master aka 上線的產品有問題(bug)時,master 會退回上一個版本止血,然而我們顯然無法把這個 bug 加到下一期的 Feature 內修正,再一路合併到 master;面對這種情況,我們會開立 hotfixes 分支來修復 bug,並在完成修復後 merge 回 master & Developer,讓這兩個永久分支的問題能夠同時被修復。
為了讓大家更好的理解,我簡單畫了開發中在 Gitflow 上會出現的事項並一一解說,另外我在解釋的時候比較喜歡以垂直的方式對齊 commit 的點,其中一部分原因是在垂直的點上,分支內部的程式碼是相同的。
如圖所示,10 月初開立 A、B 兩個 Feature 分支,用於完成不同的功能;而在 Feature-A 開發時,共同開發的 PG 則會先在本地 commit (途中的空心點),並在完成後 push 到分支上。
Feature-A 率先開發完,經 merge 回 Developer 分支,並且觸發編譯測試、以及打包部署,供 SA、Product Owner 能夠初步觀察成果。Feature-B 隨後也開發完成,一樣 merge 回 Developer 完成打包測試。
因此,開立的功能在合併到 Developer 時就會先經過驗證。
當 Feature A 與 B 都完成後,再 merge 到 Release 分支,此時也由自動或手動觸發測試環境的部署,進行最後的測試;測試完發現有少許的內容要微調,便於 Release 內修正,完成後的 commit 亦要進行相同的測試,通過後才能運行下一步: merge 回 Developer 以及到 master
當 Release merge 到 master 後,即可押上版本號,經 commit 觸發(可手動觸發)部署。
好景不常,Version 1.0 發生問題,此時會先退回上一個版本(若沒有則會視情況判斷留存或先下架),並開立 hotfixes 分支處理。當處理完後,再 merge 回 master 與 Developer 修正錯誤。
今天,我們講解了 Gitflow 的流程,然而 Gitflow 的規範後續也有被優化,出現 GitHub Flow 和 GitLab Flow 等,同時專案的架構與團隊的人數多少會影響 Gitflow 的實作。
明天起,我們會開始介紹這次的主角 Jenkins,並帶大家在 DevOps 機上搭建 Jenkins Server,後續,我們再為 ColorCodeTag 前後端在 Gitlab 上建立兩個 Repository,並將 Gitlab、Harbor 以 Jenkins 串聯起來。
當 Jenkins Pipeline 穩定後,我們便能啟用 Gitflow,讓分支對應在環境上,完成 DevOps 的實踐。