聊聊持續(xù)交付這點事兒
持續(xù)交付指的是在短周期內(nèi)完成軟件產(chǎn)品,以保證軟件保持在隨時可以發(fā)布的狀態(tài)。讓每一個變更都經(jīng)過一條自動化的檢驗流水線,來檢查每一個變更的質(zhì)量,通過就進(jìn)入下一個階段。其不是一種工具,而是一種實踐!
持續(xù)交付的共識和管理機制如下:
不要阻塞開發(fā)人員,這是實現(xiàn)持續(xù)交付的本質(zhì)理念
為每個團(tuán)隊指定構(gòu)建負(fù)責(zé)人或者發(fā)布工程師:優(yōu)化交付流水線,提升交付效率
項目狀態(tài)應(yīng)該對參與整個過程(包括構(gòu)建、部署、測試和發(fā)布)的所有人都是可見的
做好風(fēng)險管理
迭代增量式交付是有效風(fēng)險管理的關(guān)鍵
手工測試環(huán)境、試運行環(huán)境和生產(chǎn)環(huán)境總是需要嚴(yán)格的訪問控制
讓風(fēng)險識別成為每日例會的一部分
做好審計
手工測試環(huán)境、試運行環(huán)境和生產(chǎn)環(huán)境總是需要嚴(yán)格的訪問控制:指定誰能夠訪問“特權(quán)”環(huán)境。
要求每次部署都要進(jìn)行審計,以確切知道到底修改了哪些內(nèi)容。
文檔自動化、自文檔
接下來先說明實現(xiàn)持續(xù)交付的一些基礎(chǔ)設(shè)施和準(zhǔn)備工作,然后從本地開發(fā)和自動化構(gòu)建/部署流水線兩方面說明持續(xù)交付的具體實現(xiàn)。
1基礎(chǔ)設(shè)施和準(zhǔn)備工作
基礎(chǔ)設(shè)施和環(huán)境管理
讓所有測試環(huán)境(包括持續(xù)集成環(huán)境)都要與生產(chǎn)環(huán)境相似:
開發(fā)人員要把運維人員當(dāng)做重要用戶
切忌吞噬錯誤信息
使用運維團(tuán)隊熟悉的技術(shù):開發(fā)人員最早負(fù)責(zé)創(chuàng)建部署腳本,后面移交給運維團(tuán)隊負(fù)責(zé)維護(hù)
把創(chuàng)建和維護(hù)基礎(chǔ)設(shè)施需要的所有內(nèi)容都進(jìn)行版本控制
以自動化方式進(jìn)行配置和部署!
像對待生產(chǎn)環(huán)境一樣對待測試環(huán)境!
容器化技術(shù)實現(xiàn)不可變基礎(chǔ)設(shè)施
配置管理
版本控制、依賴管理、軟件配置管理:
各個環(huán)境的手工配置 -> 自動化配置
對所有內(nèi)容進(jìn)行版本控制
指定依賴庫的確切版本,不要用快照或者模式匹配版本
配置文件與二進(jìn)制文件分離
測試策略
創(chuàng)建全面的自動化測試套件:單元測試、組件測試、驗收測試,每一種測試的代碼覆蓋率都高于80%以上
每次修改都能運行一次自動化測試集合
分層測試
數(shù)據(jù)管理
把創(chuàng)建和遷移數(shù)據(jù)庫全部變成自動化過程,是部署流程的一個組成部分
讓測試自己創(chuàng)建它們所需的狀態(tài),并確保每個測試都獨立于其他測試
對數(shù)據(jù)庫進(jìn)行版本管理,使用DbDeploy這樣的工具管理數(shù)據(jù)遷移過程的自動化。
在大多數(shù)據(jù)情況下,不要在測試中使用生產(chǎn)數(shù)據(jù)集的副本。?
數(shù)據(jù)庫回滾和無停機發(fā)布
藍(lán)綠部署
大多數(shù)修改應(yīng)該是增加操作(比如向數(shù)據(jù)庫中增加新表或字段),盡可能不修改已存在的結(jié)構(gòu)
測試數(shù)據(jù)
測試的獨立性、原子性
其他類型的測試,一定不要使用生產(chǎn)數(shù)據(jù)庫的一個dump,除非有特殊情況
部署流水線中的數(shù)據(jù)管理
提交測試:快速運行,避免復(fù)雜的數(shù)據(jù)準(zhǔn)備
驗收測試:后續(xù)階段可以復(fù)用
容量測試:為測試提供足夠的輸入數(shù)據(jù),可以看做驗收測試的重復(fù)利用
主干開發(fā)
主干開發(fā)的分支模式實現(xiàn)持續(xù)交付最好的模式,但為了在主干模式下保持應(yīng)用可發(fā)布,需要做到:
每次創(chuàng)建分支,都要認(rèn)識到它帶來的成本
頻繁提交代碼合并到主干
新功能隱藏:功能開關(guān)統(tǒng)一管理達(dá)到特性隱藏的目的(Togglz?)
增量開發(fā):將所有的變更都變成一系列的增量式小修改,而且每次小的修改都是可發(fā)布的。
抽象模擬分支(無法使用增量開發(fā)):修繕者模式,使用門面模式隔離待改造代碼。
使用組件,根據(jù)不同部分修改的頻率對應(yīng)用程序進(jìn)行解耦。
2本地開發(fā)
讓開發(fā)者不受阻塞、不受不必要的干擾 -> 持續(xù)開發(fā)

確保自動化測試、構(gòu)建部署腳本都能夠在開發(fā)機上運行
本地自動化測試:預(yù)測試提交pretested commit/個人構(gòu)建personal build/試飛構(gòu)建preflight build【保證本地開發(fā)所有驗證方式與流水線上的驗證方式一致,提高開發(fā)人員在本地發(fā)現(xiàn)問題的能力】
提交前在本地運行所有的提交測試,等提交測試通過后再繼續(xù)工作
在可控的環(huán)境上部署開發(fā)的應(yīng)用程序
修復(fù)破壞應(yīng)用程序的任意修改是最高優(yōu)先級的任務(wù),構(gòu)建失敗后不要提交新代碼
六步提交法
規(guī)范開發(fā)習(xí)慣。主動提前集成;小步提交、完整代碼、不影響已有功能;關(guān)注代碼規(guī)范、動靜態(tài)掃描問題:
檢出最近成功的代碼
修改代碼
第一次個人構(gòu)建
第二次個人構(gòu)建:拉取主干代碼集成后本地測試
提交代碼到主干
提交構(gòu)建
提交不影響已有功能??!
增量迭代開發(fā)
抽象模擬分支
特性隱藏
規(guī)范化、自動化核心步驟

提高開發(fā)環(huán)境的效率:環(huán)境獲取的服務(wù)化、自助化;環(huán)境的一體化、一致性:
1、本地開發(fā)環(huán)境
共享機器池
Git提交日志插入截圖:Share Bucket+Google Drive
遠(yuǎn)程開發(fā)機器/Web IDE
依賴的服務(wù)
維護(hù)一個單獨的環(huán)境,讓開發(fā)環(huán)境接入
服務(wù)虛擬化工具來模擬依賴的服務(wù),Mountbank、WireMock
2、聯(lián)調(diào)環(huán)境:提供機器池,確保有兩套空閑環(huán)境,自助化提供給開發(fā)者使用
規(guī)范化、自動化本地檢查:
語法檢查、規(guī)范檢查、單元測試:Maven/Gradle插件
3、建設(shè)并自動化代碼入庫前的檢查流程
持續(xù)集成前的必要工作
代碼審查
代碼審查
人工代碼檢查:
統(tǒng)一并明確代碼審查標(biāo)準(zhǔn)
統(tǒng)一并明確日志提交規(guī)范
傳達(dá)團(tuán)隊的代碼規(guī)則、質(zhì)量基準(zhǔn)
LGTM(Looks good to me)
方式:
代碼入庫前的設(shè)計時檢查:在設(shè)計階段進(jìn)行代碼審查
代碼入庫前門禁檢查,需要考慮靈活性,提供繞過機制
代碼入庫后檢查
工具輔助的線下異步審查:依賴于Gitlab、Gerrit、Code Climate Engines,一對一審查
面對面審查:架構(gòu)問題、結(jié)對編程
代碼增量審查/代碼全量審查
團(tuán)隊審查:適合專項討論
代碼審查計入工作量和績效考評
代碼提交規(guī)范:
原子提交
提交日志規(guī)范
原則:
互相尊重
基于討論
相關(guān)資料可見:https://github.com/google/eng-practices/blob/master/review/index.md
快速反饋、增量開發(fā)
邊開發(fā)邊驗證
提高運行靜態(tài)檢查和測試的方便性、靈活性:Maven/Gradle插件
提供沙盒環(huán)境方便驗證和測試
容器
小范圍的增量構(gòu)建和驗證?
測試數(shù)據(jù):直接使用生產(chǎn)環(huán)境、生產(chǎn)數(shù)據(jù)的導(dǎo)出并脫敏
實時檢驗工具:IDE實時檢驗、Liveload
3自動化構(gòu)建/部署流水線
部署流水線就是對軟件交付流程的建模。

實現(xiàn)部署流水線的一些共識如下:
流水線建設(shè)原則
測試盡量完整,保證產(chǎn)品質(zhì)量->完備的測試機制
運行速度夠快->盡早反饋、提高交付速度
使用的所有環(huán)境盡量和生產(chǎn)環(huán)境一致->復(fù)現(xiàn)問題
所有相關(guān)角色提供構(gòu)建狀態(tài)可視化:持續(xù)交付流水線大屏顯示
存儲構(gòu)建結(jié)果報告
只要有環(huán)節(jié)失敗,就停止整個流水線!
制品庫是特殊的版本控制系統(tǒng),不需要保存所有版本。
為部署流水線的每個階段創(chuàng)建腳本:腳本是系統(tǒng)中的一等公民
增量式實現(xiàn)流水線:如果流程中有手工操作部分,就在流水線中為它創(chuàng)建一個占位符。
接下來從流水線的各個階段分別說明。
提交階段
從技術(shù)角度上斷言整個系統(tǒng)是可以工作的。
編譯、單元測試、組裝打包、代碼分析
少于五分鐘,一定不要超過十分鐘
提交測試:單元測試、組件測試
只有在某個錯誤讓提交階段的其他任務(wù)無法執(zhí)行時,才停下來否則就直至提交階段全部運行完后,匯總所有的錯誤和失敗報告
此階段的結(jié)果:結(jié)果報告、二進(jìn)制包、元數(shù)據(jù)
自動化驗收測試
驗證一個用戶故事或需求的驗收條件是否被滿足。針對業(yè)務(wù)!
配置環(huán)境、部署二進(jìn)制文件、冒煙測試、驗收測試
令驗收測試失敗的構(gòu)建版本不能被部署
先部署再測試,重用部署腳本。
類生產(chǎn)環(huán)境運行驗收測試:大部分是功能驗收測試,關(guān)注功能正確性
開發(fā)人員能夠在自己的開發(fā)環(huán)境中運行自動化驗收測試
測試的關(guān)注點在系統(tǒng)的行為,而非數(shù)據(jù)本身。所以抵制使用生產(chǎn)數(shù)據(jù)的備份做為驗收測試
驗收測試的性能不是主要考慮問題,重點在測試的全面性。
正確地做驗收測試:不要幼稚地對照著驗收測試條件,盲目地把所有東西都自動化。
驗收測試可以看作所有后續(xù)測試階段(包括容量測試)的某種模板:從部署準(zhǔn)備開始,然后核實環(huán)境和應(yīng)用程序都已被正確配置和部署,最后執(zhí)行測試。
后續(xù)測試
手工測試:探索性測試、易用性測試
非功能測試:性能、安全、可維護(hù)、可擴(kuò)展
部署發(fā)布
此階段的觸發(fā)不需要自動,測試或者運維人員可以做到自服務(wù)即可。
對不同環(huán)境采用同一部署方式:使用同樣的腳本向所有環(huán)境部署,包括開發(fā)機器
一鍵式部署是對環(huán)境進(jìn)行修改的唯一途徑。
部署測試:對部署進(jìn)行冒煙測試,驗證部署是否成功,證明其部署的可靠性
確保部署流程是冪等的
只有通過了自動化構(gòu)建、測試和部署的那些修改才能發(fā)布!
明確每個環(huán)境的部署和發(fā)布都是由誰負(fù)責(zé)
發(fā)布計劃:第一次發(fā)布,產(chǎn)出一些文檔、自動化腳本或其他形式的流程步驟
首次部署:首個迭代的主要目標(biāo)之一就是在迭代結(jié)束時,讓部署流水線的前幾個階段可以運行,實現(xiàn)部署流水線的“抽水泵”。
部署流水線的提交階段。
一個用于部署的類生產(chǎn)環(huán)境。
通過一個自動化過程獲取在提交階段中生成的二進(jìn)制包,并將其部署到這個類生產(chǎn)環(huán)境中。
一個簡單的冒煙測試,用于驗證本次部署是正確的,并且應(yīng)用程序正在運行。
對發(fā)布過程進(jìn)行建模并讓構(gòu)建晉級
為了達(dá)到發(fā)布質(zhì)量,一個構(gòu)建版本要通過哪些測試階段
每個階段需要設(shè)置什么樣的晉級門檻或需要什么樣的簽字許可。
對于每個晉級門檻來說,誰有權(quán)批準(zhǔn)讓某個構(gòu)建通過該階段。
將每次已通過驗收測試的變更版本部署在試運行環(huán)境中
緊急修復(fù):緊急修復(fù)版本也要走完標(biāo)準(zhǔn)的部署流水線,與其他代碼變更沒什么區(qū)別。
結(jié)對做!
有時候回滾比部署新的修復(fù)版本更劃算。
持續(xù)部署:每當(dāng)有版本通過自動化測試之后,就將其部署到生產(chǎn)環(huán)境中?!拘枰蕾噺姶蟮淖詣踊瘻y試機制】
度量
每次提交后都產(chǎn)生關(guān)于這些度量的報告和可視化效果并保存起來。
周期時間(cycle time),從決定要做某個特性開始,直到把這個特性交付給用戶的這段時間
自動化測試覆蓋率
代碼庫特征
缺陷數(shù)量
交付速度
提交版本庫次數(shù)
構(gòu)建次數(shù)
構(gòu)建失敗次數(shù)
構(gòu)建所花時間
4其他
DevOps
DevOps是這些年很流行的一個概念,其目的就是打通研發(fā)和運維環(huán)節(jié),以達(dá)到全員目標(biāo)一致,保障軟件高效交付。

職能團(tuán)隊提供平臺和工具,讓全棧工程師能夠自己處理端到端的工作,實現(xiàn)DevOps。
全棧開發(fā):工程師不再只是對某一個單一職能負(fù)責(zé),而是對最終產(chǎn)品負(fù)責(zé)。
信息溯源
打通研發(fā)流程中流動的多種標(biāo)識信息,以方便相關(guān)人員快速獲取需要的信息,提高工作效率。包括任務(wù)工單、代碼提交號、版本號、代碼審查ID、測試用例ID、Bug ID。
制品與源代碼版本管理:放置在制品包中的元數(shù)據(jù),體現(xiàn)源代碼版本號。
源代碼與需求/Bug的版本關(guān)聯(lián):提交代碼時需要在注釋里注明需求ID、測試用例ID等。
本文轉(zhuǎn)載自:「 后端技術(shù)雜談 」,原文:https://tinyurl.com/2dp6a9n3 ,版權(quán)歸原作者所有。


醒醒吧!你的價值,并不等同于你的忙碌

下手重了,我把同事小劉的腿打斷了...

因為這樣的代碼,我瘋了.....
