文章摘要: 自動建立環境和應用以及相關資料服務和Mock服務即是應用的開發和整合測試環境的快速自動化環境
背景
基於唯品會Noah雲平臺,我們已經在內部研發環境建立了一整套PaaS基礎設施,實現對開發和測試過程的支撐。通過PaaS平臺上的CI/CD流水線,實現了從程式碼到映象到環境部署的整體流程;通過自研的環境管理功能(Pandora),實現了對多種不同內部開發測試部署環境的管理,支撐業務快速建立部署環境和利用容器映象拉起應用,提高業務開發效率。
如上圖所示,我們的PaaS容器部署環境目前分為功能測試環境,聯調測試環境和迴歸測試環境三大類,其中功能測試環境包含了多個有業務開發靈活實時建立的隔離環境,用於功能驗證使用,而聯調和迴歸環境部署了所有可以上雲的應用,用於各類應用的整合大聯調以及上線前的迴歸測試驗證。各個環境間通過Kubernetes的namespace進行隔離,同時在微服務應用級別也通過我們微服務基礎設施提供的分割槽功能實現邏輯上的配置和路由隔離,從而基於同一套Kubernetes叢集提供面向業務的多個邏輯上獨立的環境。
02
功能環境與基礎設施
針對功能環境的管理,PaaS平臺的Pandora元件通過圖形化的配置介面,對使用者隔離了Kubernetes平臺的各項細節,在Noah雲基礎上極大的簡化了Kubernetes上的應用部署和管理。 主要提供了以下功能:
●邏輯隔離環境的管理;
●應用映象的部署,引數化配置和應用例項管理;
●基礎資源服務拉起:在Kubernetes叢集中為單獨環境獨立拉起Memcached,Redis,MySQL等服務;
●基礎元件設施的整合和管理:爲了支撐微服務應用生態,我們有配置中心,訊息中介軟體服務,資料庫中介軟體服務等。這些基礎服務通過邏輯分割槽的方式可以靈活的提供獨立環境支援;
●服務路由管理:在微服務架構下,為實現一個功能鏈路,單獨一個應用是無法獨立完成的,往往是需要依賴與其它的應用服務。被依賴的服務可以在環境內部直接訪問,或者通過環境依賴的配置將請求動態路由到其它預先指定的環境內的應用(這裏除了功能環境,當然也包含聯調和迴歸環境,最大層度的重用已有服務)。
儘管通過PaaS平臺的Pandora圖形界面極大的簡化了在環境建立和應用部署管理工作,應用本身的部署依賴不是單單依靠容器的編排可以解決的問題。
通常我們部署一個容器化的應用前,需要為這個應用在配置中心建立/修改相關的配置,需要為隔離環境開通訊息服務,需要準備新的資料庫、Schema和初始資料或Redis容器例項為獨立的應用服務,等等一系列的操作。
對於一個應用的業務測試部署人員而言,這些資訊相對容易獲取,但是其他人需要在一個環境中部署自己或其它開發組織開發的應用用於測試和聯調時,就必須依賴閱讀現有文件或者需求其他人的幫助以便正確配置依賴的基礎服務,這同時也是一項比較耗時和容易出錯的工作。這些準備工作往往會佔用比部署應用本身更多的時間和精力。
我們希望達到的目標是能夠非常快速的和可重複的一鍵拉起環境和應用,自動化的解決各項依賴問題,從而極大的減少人工工作,使得業務開發專注於業務的創新,從各項環境部署和管理工作中解脫出來,提高工作效率。
對於一個自動化的部署流程,我們期望是可以在分鐘級別完成整套獨立環境的建立,各項基礎服務的開通,資料資源容器的拉起和資料初始化以及應用的啟動。並且整個流程的執行是可以動態建立和監控的,從而可以同時作為一個工具服務提供給外部自動化測試以及軟體工程管理系統使用。
應用場景
對於一鍵拉起功能,主要有三大應用場景和階段:
● 應用的開發和整合測試環境: 通過版本化的環境定義,自動建立環境和應用以及相關資料服務和Mock服務,從而實現元件自動化測試中的全自動化部署
● 軟體專案的生命週期自動化的一部分: 將實際測試環境管理建立工作從開發和測試團隊工作中分離出來。開發測試只需要定義軟體相關依賴和配置,各種環境完全根據配置建立出來,並且在專案結束後自動回收。作為整體專案週期,實現從專案建立開始,關聯程式碼repo和分支,程式碼質量,部署配置,自動化測試,軟體部署環境以及專案結束週期。
● 基於Noah雲的整體CICD流程關鍵支撐: 通過將版本化的環境定義作為單一資料來源,實現研發測試流程中環境的建立測試驗證過程中配置資料的管理標準化,進而打通測試完成釋出上線步驟的配置變更自動識別生成對比,實現和推動全CICD流程自動化。
目前我們主要關注的是第一部分,即是應用的開發和整合測試環境的快速自動化環境,用於簡化開發測試階段的環境管理。
01
一鍵拉起與開發/整合測試環境
目前在業務團隊中,開發與測試還是遵循比較傳統的分工方式:開發完成程式碼修改,在測試環境或者本地完成簡單功能驗證後提交測試部署和完成測試驗收。其中的自動化過程主要有單元測試,整合測試和系統測試。通常開發只負責單元測試和部分可在本地執行的整合測試自動化,其餘涉及資料準備和環境部署的測試程式碼通常由測試團隊完成和維護。
當我們需要一個敏捷團隊以最快的速度來交付穩定的產品時,這種模式無法很好的幫助我們的業務開發團隊在保證高質量的同時提高交付速度:
●測試開發分離,需要更多的溝通和協調;
●可用環境有限,提測需要排隊,多個不同功能分支無法併發執行測試;
●反饋週期長,開發階段不能發現的問題需要等到提測合併到釋出分支後才能得到反饋。
相對傳統單元測試而言(更多偏向於單個類/檔案本身邏輯的測試),目前更多的測試用例實際上是類似整合測試的,對於環境包括資料庫、快取以及其他服務有一定的依賴。這種模式下相應帶來的好處在於我們可以更多的按照實際業務流程以BDD(Behavior-driven development)的方式來進行測試設計開發,專注於重要的業務需求。這也要求開發人員能夠更多的參與到自動化整合測試用例的設計與執行過程中去,從而更快的獲取測試執行結果,瞭解和解決出現的問題。
目前的自動化測試執行分兩類:
●類似單元測試,但是依賴資料庫/快取和簡單mock服務執行:共享外部資料庫資源,沒有隔離,容易發生衝突,需要協調;
●AutoV整合測試,需要本地啟動資料庫/快取以及依賴的服務或mock來執行:本地資源佔用大,執行和除錯比較費時,速度和體驗不佳。
對於開發階段,單個應用的自動化整合測試,主要需要關注的問題包括:
●測試環境應該儘量只包含待測應用和相關基礎服務依賴,如資料庫、快取等,其餘需要依賴的服務儘量以mock形式配置,減少不確定性和環境複雜性;
●測試環境可以隨時可重複的建立和銷燬,保證環境和測試的可重複性以及有效利用資源,更多的執行測試;
●應用的行為可以通過引數化的方式來配置或者實時控制(例如通過配置中心下發配置改變應用行為)。
同樣,對於同一產品線下面多個應用的整合測試也是需要遵循類似的原則,保證環境的可重複建立性以及通過Mock來隔離外部的依賴。
通過一鍵拉起方式管理環境,可以極大的簡化環境的部署配置工作,讓一般比較少接觸應用部署的開發人員也可以方便快速的獲取單獨的開發/測試環境,進而推動和方便開發人員編寫和執行更多的自動化測試用例,儘早發現問題,提高整體的交付效率。
解決方案與工作流程
要解決實際使用中的困難,統一定義和維護一套適配唯品會應用基礎設施實際情況的標準化應用模型是首先需要解決的問題。我們的應用模型具體會體現為應用描述的yaml檔案,可以單獨和自動化測試工程儲存在git repo,也可以與應用包和映象的版本關聯,儲存到應用目錄服務中,從而和應用一起實現版本化的同步管理。
針對我們的實際情況,應用會需要部署到不同的環境中,在不同環境需要對應用的配置按需調整,所以我們需要將應用部署描述和環境部署描述做一個分離,從而實現應用和環境描述的解耦,通過環境對應用的引用來自動化的動態組合各個應用。
對於單個應用而言,部署時除了標準的容器CPU/記憶體需求之外,還會有如下應用相關的配置元素:
●應用啟動需要的環境變數配置;
●應用在配置中心的各種變數配置;
●應用需要建立的訊息佇列;
●應用需要消費的訊息佇列;
●應用對於資料資源服務的要求: MC, Redis,Mysql,以及通過資料中介軟體接入的配置;
●應用對資料庫Schema/初始資料的配置。
相應在部署階段,會有對環境的描述要求,包括:
●環境基礎服務的依賴;
●環境資源服務:是否有公用資源服務,還是需要單獨拉起資源使用,資源如何分配給每個應用;
●環境需要部署的應用,版本,系統資源分配;
●環境依賴資訊:額外的域名解析配置,對其他環境服務的依賴,Mock服務依賴。
對於一個最簡單的環境部署配置而言,只需要宣告需要包含的應用和版本,系統應該自動根據應用部署描述生成環境配置:
●環境基礎服務依賴:預先配置好可用的基礎服務集合,部署只需要宣告需要哪一組服務;
●系統資源分配:按應用型別預設值或者使用應用最低要求;
●資源服務的拉起:按應用描述要求收集彙總,拉起共享服務供應用使用;
●環境依賴:需單獨宣告,和環境相關。
整體而言,我們需要實現:
●通過流水線生成收集版本化的應用描述模板,生成應用目錄;
●基於應用目錄,結合軟體專案,定義每個專案的環境部署需求,生成環境部署描述;
●基於應用描述和環境描述自動構建獨立部署環境和應用配置:
☛自動關聯環境依賴的各項基礎服務;
☛自動建立所需資料服務資源,並且與特定應用自動繫結;
☛自動部署應用整合版本到環境,自動處理環境更新;
☛自動處理應用對環境的各項依賴。
01
自動化測試的開發和執行
基於以上解決方案,對於開發人員,我們可以比較方便的通過環境描述的宣告來快速的獲取一個用於開發的部署環境。
在最簡單的情況下,通過宣告需要的應用版本即可快速建立一個環境供使用。需要依賴的服務,可以通過對Vmock的配置獲取Mock服務或者直接在當前環境中拉起例項使用。由於預先提供的應用描述已經包含資料庫、快取等資訊,對應的服務也會自動在這個隔離的環境中建立出來,並且初始化完成。
對於本地測試的開發,可以直接連線這個環境執行各項測試用例而不會干擾其他人的工作或者被其他正在執行的測試干擾。
對於持續整合,也可以在程式碼提交編譯通過後自動建立單獨隔離環境執行。從而快速的獲取反饋,瞭解修改帶來的影響以及是否成功完成。
同時,如果應用已經整合了Flyway的資料遷移工具,流水線可以自動打包相關遷移指令碼,從而在環境建立/應用更新過程中執行遷移,保證資料庫的自動同步,讓資料庫版本和應用版本一起管理,減少資料不一致帶來額外排查負擔。
更進一步,對於開發過程中的聯調,我們也不再需要依賴某一個特定環境。對方應用提供一個簡單的應用配置放入環境描述以後,我們就可以在隔離環境快速的獲取一個用於聯調的應用例項,更好的對介面功能進行驗證。
架構與實現
如前所述,我們在Pandora環境管理應用中實現了一鍵拉起的功能並且結合應用目錄服務提供給指令碼,專案管理工具和自動化測試使用。應用部署功能主要通過Noah提供的API實現容器映象部署,同時也通過監控Kubernetes事件來實現應用和服務啟動過程的跟蹤,驅動整個環境拉起工作流。
01
核心功能設計與實現
一鍵拉起的整體基於Pandora已經實現的環境管理功能,核心部分在於通過應用模型和環境模型的解析,根據宣告和依賴動態生成環境、應用拉起工作流,進而通過對工作流任務的併發和順序執行,完成資源準備,服務開通和應用部署等各項任務。
相對於目前公用雲和各項開源軟體提供的服務,一大優勢在於使用者無需顯式的關注一個應用或者一組應用的初始化過程,僅僅需要按照標準模型來描述應用和部署環境要求,系統會自動確定各項任務的執行順序和併發執行能力,以最快的路徑來執行應用部署流程。
對於應用的版本更新,原理是一樣的。使用者只需要提供一個環境中應用的最終版本要求,系統會自動對比差異,確定需要重新部署或者重新啟動的應用,自動完成環境更新。
02
事件監控與分散式處理轉發
工作流的執行是一個非同步過程,因此我們需要一個事件管理機制來實現事件的統一處理和轉發。這裏的事件包含多個事件來源:
●Kubernetes Events:資料基礎服務容器和應用容器的啟動監控
●服務呼叫完成事件:各基礎服務初始化,資料初始化等事件
●流程管理事件:比如取消流程執行等處理
我們使用Apache Kakfa作為統一的事件匯流排,多個Pandora流程排程器例項會訂閱該事件Topic,各自實現對當前例項內管理的流程的處理。從而可以實現動態的擴容,無需擔心大規模使用後流程的分散式管理問題。
03
資料庫的初始化與版本管理
資料的管理通常是比較複雜的。不同應用會採取不同的方式來管理Schema和初始資料。我們也提供了多種方式來相容不同的資料管理機制,包括:
●SQL指令碼;
●從集中的資料Schema治理系統獲取資料Schema;
●基於Flyway的資料自動初始化和資料遷移管理工具。
從初始資料的注入來看,由於有些應用沒有很好的維護資料指令碼,通常需要從一個基礎的測試資料庫匯出初始化的SQL指令碼。這種情況下資料集通常會比較大。我們在初始化執行過程中進行了優化,採用批量提交執行的策略,能夠快速的批量匯入資料,降低資料準備時間。
總結與使用實踐
在完成核心功能開發以後,我們和一個業務小組聯合對實際經常需要同時部署的一組應用做了試用和驗證,總體而言比較好的滿足了複雜應用部署的要求。
這一組應用的基本情況如下:
●多個應用域(7~20個),需要在同一個環境部署實現端到端的驗證;
●資源服務配置複雜,目前維護了眾多的虛擬機器:
☛MySQL,多達128個分庫。初始資料多達18000行SQL;
☛Redis:單例項/Sharding/Cluster配置並存;
☛資料庫中介軟體:不同應用多項服務註冊使用,並且有不同應用共用同一服務的情況.
●訊息佇列服務眾多,往常需要逐條Channel/Queue進行配置;
●環境變數配置工作繁重:包括多個MySQL分庫,Redis例項的配置資訊;
●經常需要切換各個應用配置適應不同測試場景。
我們從現有部署環境匯出了應用描述以後,經過簡單定義修改資料服務相關描述,快速實現了在6~7分鐘內完成所有資料庫例項的初始化和應用的配置和啟動,並且該過程是可以重複執行的,也就是說可以非常方便的隨時根據測試場景要求快速準備出測試環境,無需手工維護各項配置和應用。對於應用版本更新,由於各基礎服務已經存在,我們只需要建立新增的基礎服務以及重新部署應用,可以在1~2分鐘內完成。
推薦閱讀
唯品會Noah雲平臺實現內幕披露
「唯技術」一檔專為唯品技術人發聲的公眾號
歡迎投稿!!
只要是 技術相關的文章 儘管砸過來!