《Software Engineering at Google》, 是 Fergus Henderson(弗格斯·亨德森)在2017年6月發(fā)表,并于2019年修訂的一篇論文。這篇論文從軟件開發(fā),項目管理和人員管理的角度講述了谷歌的軟件工程實踐。谷歌作為一家全球頂尖的科技公司,在軟件工程方面有著非常出色的實踐經(jīng)歷,值得軟件工程師們認真品讀。
作者Fergus Henderson在谷歌從事了10年以上的軟件工程師崗位,從1979年還是個孩子的時候就開始編程,至今已經(jīng)有了超過40年的編程經(jīng)歷。是谷歌軟件構(gòu)建工具Blaze最初的開發(fā)者之一,如今Blaze已經(jīng)在谷歌內(nèi)部廣泛使用。他寫出的軟件如今安裝在超過10億臺設(shè)備上,每天被使用超過10億次。

以下是我個人的一些思考:
做偉大的產(chǎn)品,服務(wù)社會并賺取利潤。這大概是每個軟件工程從業(yè)者的職業(yè)目標。
軟件服務(wù)公司,將人才聚集在一起,用以支撐更大的商業(yè)價值。對公司來說,如何組織資源,調(diào)動人才,獲取最大價值,是值得思考和研究的。這也是公司存在的意義,即整合人才以達到個人難以達到的目標。
要想取得最大價值,需要做好三件事:
- 招募優(yōu)秀的人才,并把每一個人才放到合適的崗位上。
- 激發(fā)人才的內(nèi)在潛力和創(chuàng)造力。
- 以科學(xué)的方法論,指導(dǎo)推動軟件工程的實施。
關(guān)于人才
谷歌主要采用了以下兩種策略來激發(fā)人才的潛力
- 20%自由時間
- OKR管理
20%的自由時間
公司許可,工程師們可以花費20%的工作時間做任何項目,無需主管的同意。這個舉措的好處非常多。一來可以充分激發(fā)員工的創(chuàng)造力,創(chuàng)造力來源于興趣。二來,這個舉措體現(xiàn)了對工程師的足夠尊重,讓他們充分擁有歸屬感,認為在谷歌工作可以充分展示才華,而不是乏味的打工。
我自己也深有體會,在工作中,經(jīng)常會迸發(fā)出靈感,或者有非常想做的,想研究的技術(shù)點。但通常會為了工作進度而妥協(xié),或者強行擠出休息時間來進行。如果官方提供了20%的時間,相信作為工程師,一定會感到干勁十足。
目標與關(guān)鍵成果(OKR)
對團隊來說,方向感是必不可少的。谷歌采用OKR模型來把控方向,O表示Object(目標),KR表示Key Result(關(guān)鍵成果)。目標通??梢苑纸鉃?~5個關(guān)鍵成果。個人的OKR,需要和團隊的,更高層級的OKR對齊。OKR周期不宜過短也不宜過長,谷歌采用季度作為OKR周期。
很多人用KPI(Key Performance Indicator)和OKR進行對比,并認為兩者沒有本質(zhì)區(qū)別。的確,這兩者在實踐上非常容易混淆,但他們的思想確實截然不同的。KPI通常直接用來衡量業(yè)績,決定了你的收入和晉升機會。通常采用團隊認領(lǐng)的方式,主管領(lǐng)了KPI之后,將KPI分解給團隊成員,整個團隊的目標都圍繞著如何將KPI完成。由于KPI的完成程度直接等于績效,在制定KPI的時候,員工會和老板討價還價,希望制定一個較低的易于完成的KPI,這對于創(chuàng)造力來說是受限的。
OKR則不與績效直接掛鉤,僅作為參考。制定OKR的時候,鼓勵充分發(fā)揮想象力,高標準的制定。每一個員工自己思考并制定自己的OKR(需要和主管對齊),它更多體現(xiàn)的是一種自底向上的管理模式,對于發(fā)揮主觀能動性來說,具有很大的優(yōu)勢。
關(guān)于軟件工程
關(guān)于人才管理,就暫時寫到這里,我是一名工程師,還是想更多的談一談我對軟件工程這一塊的感受。
原文寫的比較散,分別從代碼管理,編譯構(gòu)建,測試,缺陷管理,發(fā)布版本,上線等必要的環(huán)節(jié),講述了谷歌內(nèi)部的做法。不得不說,谷歌在軟件工程方面做得相當出色,是業(yè)界的楷模。
不過我并不打算從每一個環(huán)節(jié)來談自己的感受。我希望能夠從一個更高的維度來理解這些環(huán)節(jié)共同解決的目標以及他們之間是如何相互聯(lián)動的。
軟件開發(fā)的最終目標是將軟件上線并提供服務(wù)。評價開發(fā)的過程是否成功,我們通常會從成本和收益兩個方面考量。以下問題的答案將決定項目是否成功。
- 從項目啟動到上線,花費了多長時間
- 項目共計投入了多少工程師,他們的薪水如何。
- 軟件在上線后遭遇了多少功能缺陷和性能缺陷,這些缺陷的影響怎么樣。
- 修復(fù)缺陷和開發(fā)新功能的代價有多大。
- 如果團隊有成員流失,對項目會造成多大的影響。
- 新成員的加入,需要花多少時間熟悉業(yè)務(wù)和代碼。
當然決定項目成敗絕不是僅僅靠技術(shù)人員能左右的,還與市場運營,銷售能力等密不可分,但現(xiàn)在讓我們把視角僅僅放在技術(shù)相關(guān)的方面。
軟件工程如何實施,將直接決定這些問題的答案。但有一點需要注意的是,我們并不能在所有的問題上都取得完美的效果。因為有些指標是互相矛盾的。
比如,投入更多的工程師,可能縮短項目的開發(fā)周期,但也意味著投入更多的成本??车舸a審核,缺陷測試,可以減少當前的開發(fā)成本,并使得項目快速上線。但會造成軟件質(zhì)量的下降,并帶來后續(xù)更大的維護成本。
《經(jīng)濟學(xué)原理》中提到人們面臨權(quán)衡取舍,是經(jīng)濟學(xué)第一大原理。在軟件工程領(lǐng)域也同樣適用。成本,效率,質(zhì)量這三者不可兼得。領(lǐng)導(dǎo)者需要根據(jù)項目背景做出權(quán)衡。

如果軟件偏底層,例如操作系統(tǒng),內(nèi)核相關(guān),就應(yīng)該在軟件質(zhì)量和運行效率方面投入更多的經(jīng)歷,因為它們通常被大量的上層應(yīng)用所使用,一旦出了問題,將會導(dǎo)致極其昂貴的代價。一個典型的例子就是華為的鴻蒙操作系統(tǒng),它是需要時間去打磨的,不應(yīng)該推出一個半成品來快速搶占市場。
但處于應(yīng)用層的軟件,策略會有所不同。決策者通常不會拘泥于一個網(wǎng)頁的打開速度是1秒鐘還是1.1秒鐘,他們希望在軟件本身沒有嚴重問題的情況下,快速上線搶占市場。至于小缺陷是可以在不斷的迭代中修補的。如果失去了市場,即便你把軟件打磨的再精品,也很難彌補經(jīng)濟損失。
谷歌的設(shè)計哲學(xué)
谷歌的軟件工程,代表了大型互聯(lián)網(wǎng)企業(yè)的高效運作方式。我們來看一看它背后的設(shè)計哲學(xué)。
機器比人便宜
雇傭一名工程師的代價是高昂的,知乎的一篇薪酬對比文章里提到谷歌工程師的平均年薪接近20萬美元。在工程基礎(chǔ)設(shè)施上,谷歌愿意動用服務(wù)器的強大算力,以節(jié)約工程師的時間。內(nèi)部變異構(gòu)建系統(tǒng)Blaze就是一個很好的例子。
在谷歌,提交一行代碼改動,往往在幾秒鐘之內(nèi)就能得到構(gòu)建好的軟件包。而其他公司這個數(shù)字可能達到分鐘級別。如果魔幻的效率背后,是一個超大型的分布式系統(tǒng)。一旦編譯任務(wù)被提交,Blaze(內(nèi)部編譯框架)就會迅速計算出,文件的改動導(dǎo)致了哪些產(chǎn)物需要重新生成,生成這些產(chǎn)物可以分解成多少個子過程,并把獨立的子過程分布到龐大的集群中并行計算。
中小型公司則更多的使用筆記本電腦或臺式機的算力完成編譯構(gòu)建,這種方式雖然也能工作,但時間開銷會大不少,工程師的幸福感也會受到影響。
規(guī)范大于靈活
獨立工作的工程師通常喜歡靈活。因為靈活總能快速的解決遇到的工程問題。他們喜歡自由組織代碼,靈活選擇依賴包的版本,隨意控制編譯構(gòu)建邏輯。但在團隊作業(yè),尤其是大型團隊中,這種做法會帶來高昂的溝通成本。
谷歌有超過10億行的核心代碼存儲在一個代碼庫中,背后依托的是性能強大的分布式文件系統(tǒng)。雖然代碼庫體量巨大,但工程師并不需要下載全部代碼,而是選擇自己關(guān)注的目錄。權(quán)限系統(tǒng)的設(shè)計也圍繞目錄展開,每一層目錄都可以設(shè)置owner和developer,下級目錄自動繼承上級目錄的權(quán)限。
中央倉庫最大的好處就是內(nèi)部系統(tǒng)可以完全基于master分支工作。避免復(fù)雜的版本管理和版本沖突。通過高效運轉(zhuǎn)的持續(xù)集成機制和測試回歸機制,保證主干分支的質(zhì)量。
構(gòu)建系統(tǒng)Blaze也對使用者提出了一系列的規(guī)范要求。以C++為例,這門語言本身設(shè)計的非常靈活,在編譯時無需告訴編譯器代碼依賴的頭文件的具體路徑,只需要告訴編譯器去哪里搜索即可。但Blaze強制要求用戶顯示制定頭文件的具體路徑。
這看起來似乎在開歷史倒車,其實不然。一方面,額外增加的規(guī)范使得編譯框架更好的掌控編譯過程,從而可以最大化的利用分布式的能力解決問題。另一方面,規(guī)范也減少了團隊的溝通成本,從而使大型項目更加順滑的開展。
越早發(fā)現(xiàn)問題越好
軟件工程從寫下第一行代碼到正式上線,通常要經(jīng)歷編碼 -> 構(gòu)建 -> 測試 -> 部署,這幾個步驟,有一種說法是缺陷每遲一個環(huán)節(jié)被發(fā)現(xiàn),解決成本平均提高10倍。谷歌有一套完整的機制,保障軟件的質(zhì)量,并推動盡早的發(fā)現(xiàn)缺陷。
第一道關(guān)卡是編譯構(gòu)建和單元測試。工程師提交代碼后,通常會自動觸發(fā)編譯構(gòu)建和單元測試。運行結(jié)果很快就會出來,當結(jié)果為失敗時,系統(tǒng)通過郵件或即時通訊工具告知工程師。工程師需要確保自己的提交在系統(tǒng)上產(chǎn)生一個運行通過的標志,否則需要高優(yōu)先級解決問題。
第二道關(guān)卡是代碼審核。代碼審核采用人工審核+機器輔助的方式,通常檢查邏輯是否有錯誤,代碼是否規(guī)范,架構(gòu)是否合理。谷歌內(nèi)部有一個自動化的系統(tǒng),會在工程師提交代碼審核后給出推薦的審核人列表,一來避免某些人被分配了過多的審核任務(wù),二來也可以把復(fù)雜的改動交給更資深的審核者。本著高效的原則,每次提交的代碼量應(yīng)該控制在300行以內(nèi)。
第三道關(guān)卡是功能測試和集成測試,在這里將對產(chǎn)品的功能有一個完整的檢測。谷歌也開發(fā)了自動化評估測試覆蓋度的工具,負載測試先于上線是Google的一條規(guī)范準則。團隊應(yīng)該制作圖表展示關(guān)鍵性指標。
總結(jié)
這篇讀后感就準備寫到這里了。谷歌有很多先進的工程理念和優(yōu)秀的工程實踐。但從公司的角度,也要結(jié)合實際情況合理借鑒,切不可盲目照搬。決策者應(yīng)該站在成本,質(zhì)量,效率的角度綜合考慮,既要考慮歷史技術(shù)負債,又要結(jié)合未來團隊規(guī)模,公司規(guī)模等等,這并不是一件簡單的事情。
我是一名軟件工程師,專注于devops領(lǐng)域,準確說細分領(lǐng)域是編譯構(gòu)建。接下來,我會分享一些在編譯構(gòu)建領(lǐng)域的心得和最佳實踐。