代碼腐爛可以避免嗎?
一個蘋果放在桌子上不理它,它會慢慢地變壞。代碼也跟蘋果一樣,會發生代碼腐爛。壞的代碼就跟壞的蘋果一樣,會更容易發生腐爛、腐爛得更快。工作時間久了,關注的角度從個人變成了團隊整體。我就會想:代碼腐爛是否真的不可避免?有什么辦法能夠避免代碼腐爛呢?
代碼腐爛可以避免嗎?
對于這個問題,我想了挺久,后面發現答案是:代碼腐爛不可避免,只不過是時間問題。 雖然很沮喪,但是卻認清了事物的本質,走上了一條正確的道路。這比起不愿意接受,然后制定錯誤的決定來得更好。
我給出代碼腐爛不可避免的結論,其實是在思考了許多之后才做出的結論。代碼質量高低取決于許多因素,包括但不限于:需求緊急程度、需求變化程度、團隊成員技術能力、團隊幸福感等等。這些因素都會從不同方面影響到代碼質量,從而造成代碼持續腐爛。
如果一個需求特別緊急,這時候我們不會考慮使用多么高深的代碼結構去實現,肯定是短平快直接開干。畢竟對于現在來說,時間才是我們真正的敵人。這時候的代碼質量肯定沒有那么高,考慮得也沒有那么全面,這時候代碼腐爛的進度條又快速往前跑了一步。
需求變化程度也會影響代碼腐爛的程度。如果需求來來回回變化特別大,那么我們很難設計一個統一的架構去適應需求。這時候就會出現分叉,分叉變得多了,代碼結構就不好理解了。代碼腐爛就自然而然發生了。
團隊成員技術能力也是一個很重要的點。很多時候我們希望大家能用更好的代碼結構,例如設計模式,例如用封裝的思路來寫代碼。但是團隊成員的能力是有區別的,有些人對代碼能力強一點,對代碼有追求,會做得很好。但是有些人能力就是差一些,很難寫出這么好的代碼。
簡單地說,希望通過某些流程規范去完全避免代碼腐爛,那是不可能的。注意,我這里說的是「完全避免」是不可能的。無論你做得多好,你的系統可能兩三年后就需要做一次重構,這太正常了。但我們可以通過一些流程規范,去減緩這種代碼腐爛的發生。
弄清楚我們的目標是完全消滅代碼腐爛,還是減緩代碼腐爛,這非常重要。只有制定了正確的目標,我們才不會做出錯誤的決策,我們制定具體行動的時候才會更有信心。
如何減緩代碼腐爛?
減緩代碼腐爛,其實有好多種辦法。但最常見、收益最高、最好落地的兩個措施,我認為是:技術方案評審、CodeReview。
編寫技術方案,簡單地說就是在你開發之前先想好技術方案。整個需求是怎么樣的,你想如何去實現這個需求?表結構你要怎么調整?數據流從前到后的流動是怎樣的?你要做哪一些改動?而技術方案評審,則是拉上熟悉這塊業務的同學,讓他們一起看看你的技術方案。看看這種實現方案是否有問題,是否有更好的實現方式?
通過技術方案評審,我們基本上可以避免出現大的需求問題,并且能確保需求改動能符合原有的系統設計。即使不得已選擇了另外一個方式,出現了設計分叉,那大家也都知道這個事情的背景,更有利于后續解決問題。
CodeReview 則是對于技術方案的最終核對。很多時候技術方案寫的是 A,但是代碼寫著寫著就變成了 B。CodeReview 的出現就可以避免這個問題。當然 CodeReview 還有很多其他好處,例如:提高代碼質量等等。
總結
代碼腐爛是不可避免的,幾乎所有系統都在發生不同程度的代碼腐爛,大多數系統在兩三年后就要做一次重構。我們能做的只是減緩代碼腐爛的速度,讓系統能夠撐得更久。而減緩代碼腐爛的方法,技術方案評審和 CodeReview 是最基本的、最好用的兩個方法。
在周志明最新的書籍《鳳凰架構:構建可靠的大型分布式系統》里,他也說到:
架構腐化與生物的衰老過程很像,原因都來自于隨時間發生的微妙變化,如果你曾經參與過多個項目或產品的研發,應該能對以下場景有所共鳴:在項目開始的時候,團隊會花很多時間去決策該選擇什么技術體系、哪種架構、怎樣的平臺框架,甚至具體到開發、測試和持續集成工具。此時就像小孩子在選擇自己鐘愛的玩具,筆者相信無論決策的結果如何,團隊都會欣然選擇他們所想選擇的,并且堅信他們的選擇是正確的。
老人的退出、新人的加入使得團隊總是需要理解舊代碼同時完成新功能的成員,技術專家偶爾來評審一下或救一救火,充其量只能算臨時抱佛腳;另一方面是代碼會逐漸失控,時間長了一定會有某些并不適合放進最初設計中的需求出現,工期緊、任務重、業務復雜、代碼不熟悉等都會成為欠下一筆技術債的妥協理由,原則底線每一次被細微地突破,都可能被破窗效應撕裂放大成觸目驚心的血痕,最終累積到每個新人到來就馬上能嗅出老朽腐臭味道的程度。
架構腐化與生物體衰老一樣,是不可避免的。老人退出、信任加入、工期緊、任務重等等原因,都是不斷欠下的技術債,我們無法避免。而對于代碼腐爛,演進式設計或許是一個可解決的方案。簡單地說:演進式設計是不追求完美,而是追求滿足一定「保質期」內的合適,讓合適的架構在合理的生命周期中發揮價值。
演進式設計是ThoughtWorks提出的架構方法,無論是代際的演進還是漸進的演進,都帶有不少爭議,它不僅是建造的學問,也是破壞的學問。Neal Ford在Building EvolutionaryArchitectures:Support Constant Change一書中比較詳細地闡述了演進式架構的思想,獲得不少關注,卻不見得其中所有觀點都能得到廣泛認可。如果你是管理者,大概很難接受正是那些正常工作的系統帶來了研發效率的下降的觀點;如果你是程序員,估計不一定能接受代碼復用性越高、可用性越低這樣與之前認知相悖的結論。
當我們思考清楚代碼腐爛這件事情之后,或許我們就能更客觀、更平和地接受系統里那些爛代碼。因為我們知道代碼腐爛是一個自然法則,是不可避免的一件事情。我們能做的是盡量減緩腐爛的速度,讓系統在合理的生命周期里發揮它的價值。
本文轉載自微信公眾號「陳樹義」,可以通過以下二維碼關注。轉載本文請聯系陳樹義公眾號。