日韩无码专区无码一级三级片|91人人爱网站中日韩无码电影|厨房大战丰满熟妇|AV高清无码在线免费观看|另类AV日韩少妇熟女|中文日本大黄一级黄色片|色情在线视频免费|亚洲成人特黄a片|黄片wwwav色图欧美|欧亚乱色一区二区三区

RELATEED CONSULTING
相關(guān)咨詢
選擇下列產(chǎn)品馬上在線溝通
服務(wù)時(shí)間:8:30-17:00
你可能遇到了下面的問題
關(guān)閉右側(cè)工具欄

新聞中心

這里有您想知道的互聯(lián)網(wǎng)營銷解決方案
持續(xù)部署,并不簡單!

這幾年,持續(xù)集成隨著敏捷在國內(nèi)的推廣而持續(xù)走熱,與之相伴的持續(xù)部署也一直備受關(guān)注。自前兩年,持續(xù)交付這個(gè)延續(xù)性概念又闖進(jìn)了國內(nèi)IT圈,慢慢開始在社區(qū)和會(huì)議中展露頭角。許多不明真相的群眾跟風(fēng)哭著喊著要“上”,而許多前CI的半吊子玩家換件衣服就接著干,有的甚至衣服都來不及換……。國內(nèi)的這些土財(cái)主如果不巧請(qǐng)了某些所謂的戰(zhàn)略家,除了建了一堆持續(xù)集成環(huán)境,以及每天嚷嚷著要這個(gè)要那個(gè),混亂的狀況在根本上沒有得到改善。本文無意費(fèi)力探討持續(xù)集成和持續(xù)交付的概念,而是打算談?wù)剬?duì)于大型軟件企業(yè),以持續(xù)集成為基礎(chǔ)實(shí)現(xiàn)持續(xù)部署(交付)時(shí),所要面對(duì)的問題以及可行的解決方案。地主老財(cái)們,夜黑風(fēng)正猛,山高路又遠(yuǎn),注意腳下……

And God Said, Let there be light: and there wa— GENSIS, Charpter 1, King James

一、起步

先來講個(gè)故事……

幾年前,一對(duì)留美的夫婦通過朋友找到我,讓我?guī)兔υ趪鴥?nèi)組建一個(gè)開發(fā)團(tuán)隊(duì),該團(tuán)隊(duì)負(fù)責(zé)為其開發(fā)一款基于社交網(wǎng)絡(luò)的客戶關(guān)系管理軟件,(暫且稱之為項(xiàng)目A)。這個(gè)項(xiàng)目除了尚不清晰的需求范圍和很緊的期限外,作為業(yè)內(nèi)人士的老公Richard根據(jù)眼下流行的軟件開發(fā)過程還提了諸多額外的要求:

  • 功能要及早交付(以便拿去和潛在的投資人洽談)
  • 功能在部署到生產(chǎn)環(huán)境前要先部署的一個(gè)測試環(huán)境(Richard要試用后給予反饋)
  • 功能必須經(jīng)過測試(長期作為軟件外包的甲方,對(duì)質(zhì)量要求嚴(yán)格)
  • 要減少后期維護(hù)的工作(美國人精貴,少雇一個(gè)是一個(gè))
  • 支持協(xié)同開發(fā)(以便維護(hù)人員及早介入)
  • ……

這正是持續(xù)集成所要解決的典型場景。針對(duì)Richard的要求,我們只要建立一個(gè)基于Hudson(現(xiàn)在叫Jenkins)+Maven +SVN 的持續(xù)集成環(huán)境(再加上持續(xù)集成所要求的測試和過程)就可以很好地滿足上述要要求,此方案的結(jié)構(gòu)如下:

對(duì)于上述方案,讓我們近距離看看各個(gè)服務(wù)器的內(nèi)部情況,以及人員在這種方案下的分工協(xié)作:

我們先談?wù)勆厦娴膱D中涉及的一些概念性問題:

1.1)編譯時(shí)依賴運(yùn)行時(shí)依賴

從字面上不難理解這兩種依賴的類型。但要注意雖然編譯時(shí)依賴常常也是運(yùn)行時(shí)依賴,但并不能推斷出一方必然是另一方。比如,在開發(fā)的過程中需要某些提供API的Jar包,而運(yùn)行時(shí)可能是具體API實(shí)現(xiàn)的Jar包。再者,被依賴的包會(huì)有其自身的依賴,因此,項(xiàng)目對(duì)這些包產(chǎn)生間接依賴(運(yùn)行時(shí)依賴),依此類推,最終形成一個(gè)依賴樹。當(dāng)項(xiàng)目運(yùn)行時(shí),這些依賴樹上的包必須全部就位。

Maven在POM中通scope來界定依賴的類型,從而幫助開發(fā)和運(yùn)維人員擺脫手動(dòng)處理依賴樹的工作,然而運(yùn)行時(shí)所依賴包最終是要安裝到生產(chǎn)環(huán)境的,這部分工作Maven并不能自動(dòng)完成。因此,一個(gè)常用方式是將運(yùn)行時(shí)所依賴的包拷貝到項(xiàng)目文件中,比如Java Web應(yīng)用的WEB-INF/lib,然后將項(xiàng)目總的打一個(gè)包。在安裝項(xiàng)目包后,修改環(huán)境變量,將這些包所在的路徑加入相應(yīng)的環(huán)境變量中,如ClassPath。

再看個(gè)例子,現(xiàn)代的操作系統(tǒng)和其它系統(tǒng)框架都考慮到了運(yùn)行時(shí)依賴樹的處理問題,比如Ubuntu的apt-get,CentOS的yum,Ruby的RubyGem,Node的npm等等。

1.2)依賴時(shí)的復(fù)雜度

項(xiàng)目除了對(duì)程序包的依賴,對(duì)于運(yùn)行環(huán)境也有些具體的要求,比如,Web應(yīng)用需要安裝和配置Web服務(wù)器,應(yīng)用服務(wù)器,數(shù)據(jù)服務(wù)器等,企業(yè)應(yīng)用中可能需要消息隊(duì)列,緩存,定時(shí)作業(yè),或是對(duì)其它系統(tǒng)以Web Service方式暴露的服務(wù)。這些可以看做項(xiàng)目在系統(tǒng)層面對(duì)外部的依賴。這些依賴有些可以由項(xiàng)目自行處理,而有些則是項(xiàng)目無法處理的,比如運(yùn)行容器,操作系統(tǒng)等,這些是項(xiàng)目的運(yùn)行環(huán)境。

總之,依賴的復(fù)雜度主要有兩個(gè):

  1. 依賴包間的版本兼容性問題。兼容性問題是軟件開發(fā)的惡夢
  2. 間接依賴,或多重依賴問題。這個(gè)問題可以類比想像一下C++中的多重繼續(xù)種出現(xiàn)的很多問題。

比如:A依賴于python 2.7,A還依賴于B,但是B卻依賴于python 3,而Python 2.7和Python 3不兼容。這是依賴中最惡心的事。

1.3)任務(wù)分工

由于項(xiàng)目簡單,因此并不需要專門的運(yùn)維人員。以一個(gè)100人左右以交付為主業(yè)(恩,就是做外包)的公司為例,由于沒有任何歷史項(xiàng)目和代碼的拖累,且各個(gè)項(xiàng)目間也沒有任何關(guān)聯(lián),故而只需要配備一個(gè)IT支持人員進(jìn)行資源方面的管理:分配機(jī)器,報(bào)修,初始化系統(tǒng),分配IP地址等。各個(gè)項(xiàng)目的運(yùn)行環(huán)境、數(shù)據(jù)庫、開發(fā)環(huán)境等都由具體項(xiàng)目的開發(fā)人員手動(dòng)完成。 環(huán)境出問題怎么辦?很簡單,涼拌——重裝系統(tǒng)。實(shí)際的運(yùn)行效果不錯(cuò)。

1.4)自動(dòng)化部署

由于Hudson這樣的持續(xù)集成環(huán)境提供了自動(dòng)編譯(定時(shí)或觸發(fā)式)的功能,而且可以在編譯過程中提供了一些擴(kuò)展點(diǎn),因此通過提供一個(gè)部署用的腳本,就可以非常容易實(shí)現(xiàn)簡單的自動(dòng)化部署。

毫無疑問,持續(xù)集成就是敏捷的魔法藥,它見效快、副作用小、業(yè)界的爭論少。每每運(yùn)用在混亂的項(xiàng)目中時(shí),幾周內(nèi)項(xiàng)目就開始持續(xù)的產(chǎn)出經(jīng)過測試的功能。對(duì)于獨(dú)立項(xiàng)目,以持續(xù)集成為中心的持續(xù)部署絕對(duì)是不二選擇。

但是,我們有沒有想過,這會(huì)是一個(gè)自動(dòng)化部署的通用解決方案嗎?持續(xù)集成應(yīng)該位于持續(xù)交付的中心嗎?

#p#

二、困境

回到我們的故事:項(xiàng)目A上線兩年后,運(yùn)營業(yè)績不錯(cuò),投資人第一輪注資后,Richard的公司進(jìn)行了擴(kuò)張,他們對(duì)項(xiàng)目進(jìn)行了重構(gòu),而且隨著用戶數(shù)量的增長,公司分別在美國、英國和日本等地建立了運(yùn)營中心,并且對(duì)亞洲市場進(jìn)行的定制功能開發(fā)(項(xiàng)目A+),接下來,公司又投入開發(fā)了團(tuán)購系統(tǒng)(項(xiàng)目B)。在獲得了新一輪投資后,各條本來比較簡單的業(yè)務(wù)和功能線上越來越復(fù)雜,需要不斷地細(xì)分,于是公司再度擴(kuò)張(開發(fā)人員達(dá)到了300人,國內(nèi)200多人,而運(yùn)維團(tuán)隊(duì)主要在美國),隨后又為項(xiàng)目A/A+的高級(jí)用戶開發(fā)了問答系統(tǒng)(項(xiàng)目C)。目前,他們正準(zhǔn)備開發(fā)手機(jī)系統(tǒng)。 看看下面的圖,公司增長的過程中,整個(gè)項(xiàng)目環(huán)境也變得復(fù)雜。(注意,這里是一種邏輯結(jié)構(gòu),而在物理層面項(xiàng)目B和項(xiàng)目A的生產(chǎn)環(huán)境可能部署在相同的機(jī)器上)。

同時(shí),原本單一的項(xiàng)目軟件結(jié)構(gòu)隨著業(yè)務(wù)系統(tǒng)的增加也不再簡單:

而軟件間的版本依賴使這個(gè)問題變得更為復(fù)雜:

現(xiàn)在,Richard的公司已經(jīng)不再是一條快樂的小魚,而是漸漸成為一直龐大的巨獸。雖然只有四個(gè)產(chǎn)品,但公司卻要支持幾百臺(tái)開發(fā)機(jī),幾十臺(tái)生產(chǎn)服務(wù)器,還有對(duì)應(yīng)的測試環(huán)境,數(shù)據(jù)庫服務(wù)器,以及幾十個(gè)開發(fā)小組,和一大堆的內(nèi)部項(xiàng)目。我們盡可以使用持續(xù)集成來為我們完成自動(dòng)化部署。但,當(dāng)我們?yōu)楦鱾€(gè)項(xiàng)目建立起持續(xù)集成環(huán)境后,它能滿足我們對(duì)于持續(xù)部署的要求嗎?我們前期的工作可以簡化我們今后項(xiàng)目的持續(xù)交付的工作的難度嗎?它需要我們?yōu)橹⒁粋€(gè)龐大的運(yùn)維團(tuán)隊(duì),還是可以讓我們能節(jié)省下每一毛錢來投入到真正的業(yè)務(wù)價(jià)值中去?

讓我們先來看看復(fù)雜的項(xiàng)目環(huán)境中的幾個(gè)場景

場景1:環(huán)境升級(jí)

項(xiàng)目A和項(xiàng)目B都依賴于Web容器,公司決定升級(jí)Web容器版本,而公司要升級(jí)的機(jī)器有上百臺(tái),依賴人肉升級(jí)已不現(xiàn)實(shí),維護(hù)團(tuán)隊(duì)因此針對(duì)各種軟件開發(fā)了相應(yīng)的自動(dòng)化腳本,但當(dāng)新的軟件出現(xiàn)時(shí),必須要開發(fā)新的腳本。而且當(dāng)同時(shí)升級(jí)若干環(huán)境軟件時(shí),則難度隨之增大,手工調(diào)度的方式極易出錯(cuò),當(dāng)升級(jí)失敗時(shí)仍需要大量人工處理。由于存在大量升級(jí)腳本,有一定的維護(hù)成本。

場景2:依賴于環(huán)境的軟件升級(jí)與回滾

針對(duì)環(huán)境升級(jí),公司為項(xiàng)目A和項(xiàng)目B開發(fā)了新的版本。但環(huán)境的升級(jí)和軟件的升級(jí)不是同步進(jìn)行,出錯(cuò)的可能性非常大(想一想間接依賴和多重依賴的情況)。當(dāng)新版本部署到生產(chǎn)系統(tǒng)時(shí),發(fā)現(xiàn)問題,需要回滾到之前的版本——所有運(yùn)行時(shí)版本都需要回滾,而且環(huán)境也需要同步回滾。幾百臺(tái)機(jī)器……

場景3:運(yùn)行時(shí)依賴

在第一節(jié)的方案中,我們將所有的運(yùn)行時(shí)依賴都打包到一起。當(dāng)項(xiàng)目依賴關(guān)系復(fù)雜時(shí),這樣產(chǎn)生的包將非常臃腫,潛在地延長了部署的時(shí)間(想一想全世有幾百臺(tái)服務(wù)器,一個(gè)部署計(jì)劃需要部署幾百兆文件的情況),而且產(chǎn)生沖突的可能性非常大,而且對(duì)于不同類型的項(xiàng)目(Java和Ruby項(xiàng)目)缺乏通用性。06年左右,Nortel可是拿Excel統(tǒng)計(jì)過運(yùn)行時(shí)依賴的,牽涉若干項(xiàng)目組,反復(fù)多次,沒有個(gè)把月真搞不定。

場景4:泛濫的部署

每個(gè)項(xiàng)目相關(guān)的持續(xù)集成環(huán)境都需要開發(fā)自己的部署腳本,重復(fù)投入大,而且各個(gè)項(xiàng)目的部署過程不一致,并且對(duì)于同一個(gè)項(xiàng)目無法同時(shí)滿足不同目的部署要求,例如,環(huán)境或系統(tǒng)配置參數(shù)改變后,無需安裝包,只需做清理和激活的工作。最后,持續(xù)集成只是支持了和代碼修改有關(guān)的部署。

場景5:不一致的環(huán)境

簡單項(xiàng)目中,開發(fā)環(huán)境和運(yùn)行環(huán)境都由開發(fā)人員搭建,當(dāng)公司變大時(shí),系統(tǒng)的運(yùn)行環(huán)境將由運(yùn)維人員搭建,而開發(fā)環(huán)境如果由運(yùn)維人員搭建則工作量太大,由開發(fā)人員自己搭建則操作復(fù)雜又容易產(chǎn)生不一致的情況。

場景6:熱切換

對(duì)于某些部署,需要盡量減少服務(wù)的停止時(shí)間,需要在服務(wù)的同時(shí)進(jìn)行部署。

這些場景只是以持續(xù)集成為中心的持續(xù)部署在面對(duì)大型企業(yè)時(shí)所遇到的部分問題。大型企業(yè),人多,項(xiàng)目多,機(jī)器多,項(xiàng)目環(huán)境復(fù)雜,部署維護(hù)工作繁多。以持續(xù)集成為基礎(chǔ)的部署可以解決各個(gè)項(xiàng)目的集成問題,卻無法幫助企業(yè)應(yīng)對(duì)復(fù)雜的項(xiàng)目環(huán)境和各種不同的部署要求。究其更本,大型企業(yè)中的部署不再是一個(gè)簡單的問題,而是一個(gè)交付生態(tài)圈,基礎(chǔ)設(shè)施和環(huán)境管理必須要納入考慮之中。要實(shí)現(xiàn)真正意義上的持續(xù)部署,我們就必須把環(huán)境和項(xiàng)目同等對(duì)待,通通納入管理之中。同時(shí),部署本身要得到統(tǒng)一。一個(gè)好的部署機(jī)制,應(yīng)該是易于建立,易于使用,易于維護(hù)。

#p#

三、任脈——環(huán)境管理

什么是環(huán)境?

系統(tǒng)運(yùn)行所依賴和包含的一切就是其環(huán)境:硬件、操作系統(tǒng),網(wǎng)絡(luò)資源(IP地址、域名),服務(wù)容器,服務(wù)器軟件配置,環(huán)境亦是,運(yùn)行時(shí)依賴的命令和包,項(xiàng)目本身的包和配置都是環(huán)境的一部分。對(duì)于部署而言,廣義上,這些通通應(yīng)該納入環(huán)境管理的范疇,但狹義上,從軟件系統(tǒng)的角度看,一個(gè)環(huán)境就是其運(yùn)行需要的軟件及其配置(我們先把操作系統(tǒng)和網(wǎng)絡(luò)資源當(dāng)做基礎(chǔ)設(shè)施,其在部署時(shí)已處于就位的情況)。因此:

項(xiàng)目A的生產(chǎn)環(huán)境 = 項(xiàng)目A本身的軟件包 + 項(xiàng)目A運(yùn)行時(shí)依賴的軟件包 + 項(xiàng)目A運(yùn)行時(shí)依賴的其它軟件 + 項(xiàng)目A的配置信息

由于,項(xiàng)目本身的軟件包、項(xiàng)目運(yùn)行時(shí)依賴的軟件包,以及項(xiàng)目運(yùn)行時(shí)依賴的其它軟件在本質(zhì)上沒有區(qū)別——都是軟件,上面的定義可以進(jìn)一步抽象為:

環(huán)境 = 軟件包 + 配置信息

在這個(gè)定義下,我們就必須將運(yùn)行環(huán)境的軟件解構(gòu),并以包的形式導(dǎo)入到公司的整個(gè)項(xiàng)目資源庫中,比如Apache將作為一個(gè)包被導(dǎo)入,而Apache 依賴的其它包也將依次被導(dǎo)入,并建立起正確的依賴關(guān)系。而且,在導(dǎo)入的過程中還必須做些相應(yīng)的調(diào)整,如,環(huán)境變量的讀取和設(shè)置,必須來自于環(huán)境配置模塊,而不要修改系統(tǒng)的環(huán)境變量,防止不同環(huán)境在系統(tǒng)環(huán)境配置上相互影響和依賴。

再回頭審視我們的示例,項(xiàng)目A的生產(chǎn)環(huán)境可以部署在不同的區(qū)域,對(duì)于各個(gè)區(qū)域可能有定制化的設(shè)定。這就像面向?qū)ο笾械念?,可以通過繼承使子類重用父類的公有屬性和行為并添加自己特有的信息。因此,環(huán)境的概念模型如圖:

通過這樣的關(guān)系,我們很容易為示例的復(fù)雜環(huán)境建立一種簡單的結(jié)構(gòu),對(duì)于項(xiàng)目A:

這里,環(huán)境依然是處于知識(shí)層面(Knowledge Level),它并未與具體的基礎(chǔ)設(shè)施相關(guān)聯(lián)。當(dāng)我們將一個(gè)環(huán)境“具現(xiàn)化”成一個(gè)運(yùn)行系統(tǒng)時(shí),我們就產(chǎn)生了一個(gè)真正的環(huán)境實(shí)例。在這兩者之間,我們還必須要考慮環(huán)境實(shí)例的使用目的(開發(fā)?測試?……)以及安裝所依賴的其它信息(如機(jī)器),因此,我們需要增加一個(gè)環(huán)境目標(biāo)來集中這些信息,而且由于不同目標(biāo)的環(huán)境可能會(huì)有所差別,因此,環(huán)境目標(biāo)也需要配置的能力。概念模型如圖:

圖中的環(huán)境實(shí)例是如何產(chǎn)生的呢?部署,一次部署可能會(huì)產(chǎn)生一個(gè)環(huán)境實(shí)例。一系列部署將產(chǎn)生對(duì)應(yīng)于環(huán)境目標(biāo)的多個(gè)環(huán)境實(shí)例,除去當(dāng)前起作用的環(huán)境實(shí)例外(最新的),其它的是歷史環(huán)境實(shí)例。通過在歷史環(huán)境實(shí)例中切換,我們自然而然的就可以使整個(gè)環(huán)境回滾,因?yàn)轫?xiàng)目所依賴的一切都已經(jīng)成為的環(huán)境中的軟件包,而且環(huán)境依賴的包的版本會(huì)隨著部署具體確定下來。如此一來,我們便可以給每個(gè)環(huán)境實(shí)例分配一個(gè)版本號(hào),再通過環(huán)境實(shí)例的版本號(hào)與軟件包的版本對(duì)應(yīng)起來,從而得知一次部署時(shí)應(yīng)用的具體軟件包,如圖:

目前的環(huán)境管理結(jié)構(gòu),已經(jīng)可以解決場景1、2和5的問題。那么對(duì)于場景2,運(yùn)行時(shí)依賴,環(huán)境管理應(yīng)該如何解決呢?

細(xì)心的朋友,可能已經(jīng)發(fā)現(xiàn),在環(huán)境層面上我們確定了環(huán)境依賴的軟件包,這里有兩個(gè)隱藏的含義:

  • 環(huán)境定義的是對(duì)軟件包的運(yùn)行時(shí)依賴
  • 由于環(huán)境是一個(gè)邏輯上的概念,因此其所用的軟件包也是一個(gè)邏輯上的概念(相對(duì)于版本控制系統(tǒng)中的軟件包)

我們也已經(jīng)知道,在部署時(shí),一個(gè)環(huán)境實(shí)例將具體的確定其依賴的軟件包的版本。某個(gè)版本的軟件包最終與代碼庫中的物理的軟件包相關(guān)聯(lián)。但軟件包是運(yùn)行時(shí)的安裝包,因此,它應(yīng)該是代碼庫中包編譯的結(jié)果。在對(duì)代碼庫的包編譯時(shí),既要將結(jié)果打上版本保存起來,也好在兩者的版本間建立關(guān)系,最后,編譯結(jié)果應(yīng)該是某種既定的安裝包目錄文件結(jié)構(gòu)。

另外,當(dāng)環(huán)境包含的包比較多時(shí),運(yùn)行時(shí)版本樹會(huì)非常大,手動(dòng)的指定全部的包的版本將是一個(gè)非常大的體力勞動(dòng),這部分工作也要得到簡化。由此,我們必須

  • 建立邏輯軟件包版本和版本庫中軟件包版本間的關(guān)系
  • 為相互依賴的包編譯并打上統(tǒng)一的標(biāo)簽
  • 簡化運(yùn)行時(shí)包依賴關(guān)系的生產(chǎn)
  • 簡化運(yùn)行時(shí)包依賴的指定(可參考apt-get和RubyGem,環(huán)境只需指定直接依賴的包,間接依賴的包從運(yùn)行時(shí)依賴樹中自動(dòng)導(dǎo)入)

一個(gè)可能的簡單結(jié)構(gòu)如下:

上述討論還沒有涉及操作系統(tǒng),如果我們的運(yùn)行機(jī)器要支持多個(gè)系統(tǒng),我們又該怎么辦???

配置信息也是個(gè)大問題,大家可以思考

  • 環(huán)境配置和應(yīng)用配置如何區(qū)分?
  • 如何簡化環(huán)境配置工作?
  • 如何使環(huán)境配置的效果只對(duì)具體環(huán)境有效,而不會(huì)泄露到環(huán)境外部?

再者,

  • 如何使應(yīng)用支持多運(yùn)行目標(biāo)?
  • 環(huán)境管理如何能方便開發(fā)環(huán)境的調(diào)試?
  • 要如何簡化版本的選擇?
  • 在多個(gè)包有編譯和運(yùn)行時(shí)依賴時(shí),編譯時(shí)如何檢查以減少引入兼容性問題的風(fēng)險(xiǎn)?

這些都留待大家思考。

#p#

四、督脈——部署系統(tǒng)

《持續(xù)集成》和《持續(xù)交付》中都對(duì)部署有詳細(xì)的討論,不在贅述。在我看來,部署其就是按照其目的執(zhí)行一系列步驟將環(huán)境置于其目的所指向的狀態(tài)中。我們一會(huì)再回國頭來看這段文縐縐的話,先看看第一部分持續(xù)集成的環(huán)境下,我們部署的步驟可能會(huì)是下面這個(gè)樣子:

  1. 登陸目標(biāo)機(jī)(ssh)
  2. 停止服務(wù)
  3. 清理環(huán)境
  4. 準(zhǔn)備安裝環(huán)境(創(chuàng)建文件夾等)
  5. 安裝項(xiàng)目包(rsync,解壓,權(quán)限設(shè)置等)
  6. 配置環(huán)境變量
  7. 啟動(dòng)服務(wù)
  8. ……

而在第二部分的情景4中,我們看到如果對(duì)不同的持續(xù)集成環(huán)境建立不同的部署腳本和環(huán)境維護(hù)腳本,這部署過程的維護(hù)會(huì)非常繁瑣?;诘谌糠值沫h(huán)境管理,我們可以將部署過程抽象為:

現(xiàn)在回到開頭那個(gè)文縐縐的描述:部署其就是按照其目的執(zhí)行一系列步驟將環(huán)境置于其目的所指向的狀態(tài)中。

由于我們已經(jīng)將部署作為環(huán)境管理的一部分,而環(huán)境又是對(duì)外提供服務(wù)的最小實(shí)體,因此,對(duì)環(huán)境的部署就是要根據(jù)部署的類型,在環(huán)境上按一定的步驟執(zhí)行一系列操作,從而使環(huán)境置于部署類型所要的狀態(tài),這個(gè)過程中可能會(huì)生成對(duì)應(yīng)的環(huán)境實(shí)例。舉例來說,我們可能會(huì)修改環(huán)境相關(guān)的一些配置,然后重啟環(huán)境,顯然,這種情況下不需要下載安裝軟件包(沒有改變),因此也就不需要生成環(huán)境實(shí)例。

對(duì)于標(biāo)準(zhǔn)的部署——安裝軟件包并啟動(dòng)環(huán)境,可能的步驟將會(huì)是:

  1. 選擇將要部署的軟件包的版本
  2. 生成新的環(huán)境實(shí)例(確定環(huán)境實(shí)例的版本和其依賴包的版本,確定環(huán)境配置等)
  3. 清理和準(zhǔn)備目標(biāo)機(jī)環(huán)境
  4. 下載包
  5. 設(shè)置環(huán)境配置
  6. 環(huán)境實(shí)例切換
  7. 生成部署報(bào)告
  8. ……

好,部署系統(tǒng)和環(huán)境管理各就各位,我們可以將各個(gè)項(xiàng)目環(huán)境納入我們的環(huán)境管理之中,甚至是持續(xù)集成環(huán)境本身。再補(bǔ)充一句,要讓部署系統(tǒng)和環(huán)境管理能很好的發(fā)揮作用,我們即需要一個(gè)簡單一致的UI界面(為開發(fā)人員),也需要提供一個(gè)清晰明了的服務(wù)接口(供外部系統(tǒng)調(diào)用,如持續(xù)部署系統(tǒng))。對(duì)于與環(huán)境管理相關(guān)的機(jī)器狀態(tài)管理,網(wǎng)絡(luò)資源的配置等等,本文不再涉及,大家可以自己思考。環(huán)境管理的實(shí)現(xiàn)、編譯系統(tǒng)改造以及持續(xù)部署的具體實(shí)現(xiàn),另作文章探討。

就技術(shù)而言(不考慮圍繞持續(xù)部署的過程實(shí)踐),環(huán)境管理、部署系統(tǒng)以及我們沒有提及的編譯系統(tǒng)改造才是生產(chǎn)線的真正引擎,持續(xù)部署不過是水到渠成的傳送帶而已。

五、沒完

打通了任督二脈后,事還還沒有完,還有很多細(xì)節(jié)上的問題。你想,這個(gè)工具實(shí)在是太好用了,于是公司里成百上千的工程師們都在使用這個(gè)自動(dòng)化部署系統(tǒng),我們又會(huì)面對(duì)很多很多問題:

  • 部署系統(tǒng)的性能問題。幾百號(hào)人不停地在把他們的軟件部署到自己的機(jī)器上,部署到測試環(huán)境,部署到生產(chǎn)環(huán)境,一天之內(nèi)一個(gè)人可能會(huì)要部署N次,回滾N次,不但有大量部署請(qǐng)求,還有大量的文件在網(wǎng)絡(luò)上傳輸。你得想想這套部署系統(tǒng)如何解決這些性能問題,還得考慮未來更大規(guī)模的性能水平擴(kuò)展問題。
  • 目標(biāo)機(jī)環(huán)境的管理。在目標(biāo)運(yùn)行機(jī)上需要解決幾個(gè)問題:1)兩個(gè)環(huán)境間如果有一些的一樣的包,那就沒有必要再下載了,這樣可以節(jié)約時(shí)間。2)每次部署都需要把老的部署環(huán)境給保留下來,這樣方便在新舊環(huán)境下的切換。這兩點(diǎn)對(duì)于在生產(chǎn)環(huán)境下部署非常關(guān)鍵。(這需要環(huán)境內(nèi)所有軟件的綠色安裝才能更容易達(dá)到這個(gè)目標(biāo),因些,Unix/Linux會(huì)比Windows更容易做到這點(diǎn))
  • 部署一致性事務(wù)問題。有時(shí)候,我們需要同時(shí)部署若干臺(tái)服務(wù)器,比如:包A到機(jī)器MA,包B到機(jī)器MB,包C到機(jī)器MC,……(Web Service的SOA架構(gòu)),這些包之間有運(yùn)行依賴性和兼容性問題,要么一次性全部完成,要么就全部失敗。回滾也是一樣的,這是一個(gè)部署事務(wù)或部署一致性的問題。如何解決呢?
  • 部署環(huán)境的版本控制問題。前面說過,我們的一個(gè)環(huán)境就會(huì)和若干個(gè)包的版本耦合,環(huán)境必需管理要部署的包的版本。于是,當(dāng)你的部署越來越多的時(shí)候,各個(gè)環(huán)境的包的版本開始出現(xiàn)混亂,各種依賴間的版本也會(huì)出現(xiàn)不統(tǒng)一的情況,也就是說,就算你有這樣的一個(gè)工具,在一個(gè)高速開發(fā)的環(huán)境下,我們的部署環(huán)境的管理還是會(huì)出現(xiàn)很多混亂的情況,需要你不斷地統(tǒng)一大家的開發(fā)、測試環(huán)境。
  • 部署計(jì)劃。我們可能會(huì)有很多部署計(jì)劃,比如:設(shè)定定時(shí)部署,提升或降低部署優(yōu)先級(jí),部署事務(wù)定義,部署策略(如:先部署10%的機(jī)器,如果沒有問題,再把剩下的系統(tǒng)部署了),熱切計(jì)劃和策略…… 等等 ,等等 。
  • 部署的監(jiān)控和維護(hù)。任何軟件和系統(tǒng)都會(huì)有這樣的問題,當(dāng)規(guī)模上去了以后,我們的自動(dòng)化部署系統(tǒng)的監(jiān)控和維護(hù)的復(fù)雜度并不亞于一個(gè)大型的互聯(lián)網(wǎng)應(yīng)用。

這樣的問題會(huì)有很多,基本上來說,
這樣一個(gè)持續(xù)集成持續(xù)部署的自動(dòng)化系統(tǒng)并不是那么簡單的事,其開發(fā)工作量和一個(gè)標(biāo)準(zhǔn)的大型互聯(lián)網(wǎng)業(yè)務(wù)系統(tǒng)沒什么兩樣

六、總結(jié)

這里只談一點(diǎn)自己的看法,從傳統(tǒng)的持續(xù)集成到面向大型軟件的持續(xù)部署,我們將系統(tǒng)所依賴的軟件環(huán)境和軟件包抽象為一致的實(shí)體納入到管理之中,并將運(yùn)維人員的工作真正的分?jǐn)偟介_發(fā)人員身上。而云計(jì)算的出現(xiàn),使得計(jì)算機(jī)本身也可以自動(dòng)化的創(chuàng)建和回收,這樣環(huán)境管理的范疇將進(jìn)一步擴(kuò)充。相應(yīng)的,部署的能力和靈活性也是一次質(zhì)的飛躍,將再一次減輕運(yùn)維人員的工作壓力。

說了這么多廢話,總結(jié)一下自己的觀點(diǎn),對(duì)于向大型軟件企業(yè)推銷基于持續(xù)集成的持續(xù)部署(交付)的哥們:

  • 你就是在耍流氓,如果你不解決環(huán)境管理?。?!
  • 你就是在耍流氓,如果你不建立部署系統(tǒng)?。?!
  • 你就是在耍流氓,如果你不擴(kuò)展編譯系統(tǒng)?。?!
  • 你就是在耍流氓,如果你只是推銷小團(tuán)隊(duì)的實(shí)踐而不考慮改造大環(huán)境?。?!
  • 你就是個(gè)流氓,如果你只是不斷地告訴別人怎么做,自己卻從來不動(dòng)手寫一個(gè)測試或建立一個(gè)持續(xù)集成環(huán)境?。?!

最后,用Linus最經(jīng)典的話來結(jié)束本文——“ Talk is Cheap, Show me the Code!”


分享名稱:持續(xù)部署,并不簡單!
網(wǎng)站網(wǎng)址:http://m.5511xx.com/article/dpojhjo.html