遺留系統(tǒng)改造-開篇

遺留代碼

從何而來

軟件是如何演變成遺留代碼?

  • 初期,架構(gòu)清晰,代碼精煉,指點(diǎn)江山
  • 中期,新功能簡(jiǎn)單在原有代碼加上邏輯,頁(yè)面自測(cè),談笑中高效完成
  • 最后,另一個(gè)團(tuán)隊(duì)接手
    • 面對(duì)難以理解的復(fù)雜代碼,新增功能異常困難。
    • 他們?nèi)缗R大敵,為避免更多的坑,選擇繼續(xù)在原有代碼上堆積邏輯,但結(jié)果卻是導(dǎo)致更多的bug,一首《涼涼》蕩氣回腸。
    • 他們一邊在批評(píng)著前人,一邊在不堪負(fù)重的代碼繼續(xù)挖坑,漸漸變得與前人一樣……

定義

為什么大部分系統(tǒng)最后都變成了沒有活力的遺留系統(tǒng)?

因?yàn)殚_發(fā)人員成日奔波在填坑之中,新功能根本無暇顧及或者無法輕易添加。

系統(tǒng)缺失了一個(gè)最關(guān)鍵的東西:測(cè)試

因?yàn)闆]有編寫測(cè)試的代碼就是遺留代碼。

改變

為什么大家不愿意為遺留代碼編寫測(cè)試?

因?yàn)樵瓉泶a難以理解,心生敬畏且無從下手,加之bug絡(luò)繹不絕,根本無暇顧及。

忍無可忍的開發(fā)者,含淚揮刀自宮——重新寫一套系統(tǒng)。但由于缺少測(cè)試,慢慢又變成另一個(gè)遺留系統(tǒng)。

仿佛《恐怖游輪》般的結(jié)局。

如何破局?或許你應(yīng)該先試試重構(gòu)。

重構(gòu)

為什么要重構(gòu)

風(fēng)險(xiǎn)與收益

  • 軟件是高風(fēng)險(xiǎn)和多變性
  • 重構(gòu)可以降低成本
    • 改善設(shè)計(jì)
    • 更快添加新功能
    • 更少產(chǎn)生問題
    • 更快定位問題

個(gè)人成長(zhǎng)與挑戰(zhàn)

  • 通過重構(gòu)糟糕代碼來培養(yǎng)良好習(xí)慣
  • 保持既有行為不變是軟件開發(fā)最有挑戰(zhàn)的任務(wù)之一
  • 我們可能無法選擇好的項(xiàng)目,但我們可以選擇好的挑戰(zhàn)

何時(shí)重構(gòu)

  • 當(dāng)關(guān)鍵代碼維護(hù)不善的時(shí)候
  • 當(dāng)唯一理解代碼的人沒空的時(shí)候
  • 當(dāng)有信息可以揭示更好的設(shè)計(jì)的時(shí)候
  • 當(dāng)修復(fù)bug的時(shí)候
  • 當(dāng)需要添加新功能的時(shí)候
  • 當(dāng)需要為遺留代碼寫文檔的時(shí)候
  • 當(dāng)重構(gòu)比重寫容易的時(shí)候

考慮問題

我們?cè)谥貥?gòu)時(shí)需要考慮各個(gè)方面,修改遺留代碼永遠(yuǎn)是一件危險(xiǎn)的事情。

多問問自己:

  • 哪些需要修改?
  • 如何驗(yàn)證正確完成修改?
  • 如何確保沒有破壞既有功能?
  • 如何避免修改帶來越來越難以理解的代碼?

正確重構(gòu)

  • 從已有系統(tǒng)中學(xué)習(xí),只重構(gòu)熟悉的功能
  • 循序漸進(jìn),一次不要重構(gòu)過多
  • 在遺留代碼中添加測(cè)試,單元測(cè)試是重構(gòu)最有力的保障
  • 有更好的理解后對(duì)一個(gè)實(shí)現(xiàn)進(jìn)行重新設(shè)計(jì)

單元測(cè)試

好的單元測(cè)試

  • 快速反饋,十分之一秒都算慢
  • 重構(gòu)后能夠快速定位問題所在
  • 以行為作為單元,而不是代碼量
    • 一個(gè)獨(dú)立可驗(yàn)證的行為
    • 產(chǎn)生可觀察的影響
    • 不與其他行為耦合
    • 行為不變,測(cè)試也不變
    • 成為活文檔
  • 單元測(cè)試也是代碼,與其他代碼同等質(zhì)量要求
    bad:testConstructor
    good:testRetrievingValuesAfterConstruction
    

編寫策略

全新功能

采用測(cè)試驅(qū)動(dòng)開發(fā)(TDD),需要我們改變習(xí)慣——從做什么開始,再關(guān)注怎么做。

編寫步驟:

  • 先設(shè)計(jì)測(cè)試,可在任何時(shí)候進(jìn)行
  • 設(shè)計(jì)接口,確定方法名稱、收入?yún)?shù)、返回值
  • 編寫測(cè)試
  • 實(shí)現(xiàn),重構(gòu)

遺留代碼

解除依賴性以使遺留代碼改動(dòng)更容易,所以要編寫測(cè)試,往往需要先修改代碼。

編寫步驟:

  • 確定改動(dòng)點(diǎn)
  • 找出測(cè)試點(diǎn)
  • 解依賴,為測(cè)試創(chuàng)造空間
  • 編寫測(cè)試
  • 修改,重構(gòu)

關(guān)于bug

最后我們聊聊bug,解決bug最好的方法,就是避免Bug的出現(xiàn),這就要求我們編寫高質(zhì)量代碼。

如果功力不夠,那就盡早發(fā)現(xiàn)bug,依賴持續(xù)集成,自動(dòng)化測(cè)試。

設(shè)計(jì)時(shí)打印關(guān)鍵日志信息,讓bug更容易找到。

每發(fā)現(xiàn)一個(gè)bug,就當(dāng)作一項(xiàng)缺失的測(cè)試。

利用發(fā)現(xiàn)的缺陷修正流程,不斷從錯(cuò)誤中學(xué)習(xí)。

后續(xù)

后續(xù)章節(jié)將重點(diǎn)關(guān)注如何對(duì)遺留代碼進(jìn)行測(cè)試,為重構(gòu)保駕護(hù)航。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

友情鏈接更多精彩內(nèi)容