寫程式碼之前應該做的幾件事
作為程式設計師,剛剛開始學會寫程式碼,常常是接過需求就開始擼程式碼。有時候發現,寫完程式碼,需求變了。更多時候,覺得寫業務程式碼枯燥無聊,沒有技術含量。另外一邊的事實卻是,專案裡面研發人數變多了,專案的質量缺卻變低了,多人開發也不過是一個個單打獨鬥的組合而已。
1 研發環境日益成熟
經歷過 PC 網際網路的不斷深入發展,移動網際網路的蓬勃生長,網際網路進入了成熟繁榮期,研發環境也發生了巨大變化;從原來一個人,一把鍵盤,寫完程式碼就上線,變成了更加規範的研發體系和更多人參與的共同協作。
研發流程不斷加速
為了儘可能提高需求交付速度,跟上市場的變化,我們透過不斷提搞軟體交付的速度,儘可能的,從需求,編碼實現,測試,釋出的流程中不斷最佳化,利用 CICD,加速迭代。
多人協作無處不在
現在的軟體開發團隊,即使再小,也有 2-3 人一起研發,更別提測試,運維,運營,產品人員。一方面是軟體產品的競爭日趨激烈,需求日益複雜,堆砌人力成了必然;另外一方面是專業性的要求,精密的行業自然要求精細化的職業劃分。
2 困局
研發流程的速度提上去了,團隊的人也變多了,但是,需求變更依舊讓廣大研發同學感到痛苦,專案質量還在日益變差。
需求變更之痛
需求變更的痛苦為難了廣大研發同學,前腳剛為了最佳化效能,採用了 kv 儲存,後腳需求就變成了要支援模糊查詢;這是一種典型的架構設計不合理,導致業務需求的實現方式受限。
更令人痛苦的,還有產品需求變動多,今天簡單實現下,上線看看效果,明天使用者脾氣很大提了個訴求,再加一個功能上線,產品功能變成補丁加補丁。一方面是研發同學渴望一個完整又嚴謹的需求,提完需求進入研發階段就不許改;另一方面是產品同學受到各方面的壓力,只希望先把主要問題解決下,細枝末節以後再說。
專案質量變差
專案質量變差,一部分歸功於補丁程式碼的產生,迫於時間受限,先上一個補丁,卻開啟了破窗的先鋒,下一次,下一個同學就更敢於加補丁程式碼。一個個臨時的 if else 不斷堆砌,最終導致了整個專案的程式碼腐爛。我曾經維護過一個程式碼片段,超過 20 個 if else,中間還有些過時的錯誤註釋夾雜其中,維護起來令人苦不堪言。
專案程式碼腐爛的另外一個原因是多人協作,團隊的人越多,程式碼反而變得越爛似乎成為了趨勢;為什麼多人協作沒有提高程式碼質量呢?一方面,多人協作實際上只是分攤的需求實現而已,大多數需求實現的分配中,反而儘可能將協作變少,避免實現受阻。另外一方面是,不同人的程式碼模組,設計意圖和程式碼風格也截然不同。維護前人程式碼,如果沒有全域性視角,瞭解設計意圖,也只能是往裡面加補丁程式碼了。
專案程式碼腐爛容易導致程式設計師出現錯覺,一是業務程式碼沒什麼料在裡面,不如搞基礎建設;二是業務需求不可能完整又嚴謹,最終也會變來變去的,最終質量低下的鍋,一大半要給提需求的人。
3 怎麼辦
在寫程式碼之前要進行設計和建模。相比歷史短暫的 IT 行業,很多工業,建築行業的精密性,都離不開前期的設計,在分析設計之後,按照圖紙規劃施工,寫程式碼也應當如此。
設計建模的有效性源於,一,重新回到業務的跑道,跟業務一致;二,設計建模才能讓協作真實有效;
為什麼研發實現需求跟業務一致很重要呢?研發和業務需求的摩擦,本質是研發實現跟實際需求不一致,無論是研發走偏了,沒有理解需求,還是需求本身不能滿足涉眾的利益,都會使得最終上線的功能需要回爐重造,折磨專案組的成員。業務專案,需求很重要,是整個專案質量的源頭,源頭的問題不處理好,會一直髮散擴大,問題傳遞到尾部,甚至到了產品上線,對整體造成的損耗越大。從設計的語言上看,設計的層次有所不同,不僅僅有程式碼細節上的設計,也有業務上高層次的設計,高層次的設計是用業務的術語去表達,最貼近業務實際情況,也能幫助研發同學發現業務中不合理的點。
設計建模為何能讓協作真實有效?我早先體驗的協作流程,無非就是各自工作在自己的領域內部,彼此儘量減少要協作的內容,避免過多阻塞。研發側的協作,因為缺乏設計,不好分工,另外一方面,多人寫同一個模組,也會引發衝突,所以更多將協作放在在 code review 上。但 code review 作用範圍也有限,一方面,review 成本較高,逐行閱讀程式碼來釐清設計對程式碼質量要求很高,另一方面,review 時間節點往往發生較晚,臨近釋出的時候,調整設計也不大可能。進行設計建模能夠讓協作變得有效,一方面,設計建模前期是溝通和資訊對齊,將協作的內容提前,一方面,採用合適的圖形化工具,review 的成本是相對較低的。
4 怎麼設計和建模
設計和建模分為好幾個部分
業務建模,關注業務,不關注具體的實現 系統建模,關注所建設系統的邊界,找準在業務中的系統的職責和約束 分析與設計,定位核心領域,找到實際的類,釐清類的職責和類之間的關係,透過設計使得程式碼抽象複用
業務建模
總體上來說,業務建模主要聚焦於分析涉眾利益,釐清業務流程。從工具上來說,主要是用例圖,流程圖;從內容上來說,主要是找人(利益涉眾,系統執行者),找業務實體(其餘系統,相關的重要物件)。
分析涉眾利益
分析涉眾利益之前,需要找到涉眾,一般要經歷以下步驟:
找到軟體產品的願景,願景表達了軟體產品帶來的核心意義 找到利益相關的的涉眾和其利益訴求
表格是一個很好的表達方式,我負責的一個商戶從第三方商城採購刷臉裝置,由倉配系統配送裝置的業務,可以表達如下:
願景:將裝置更多更快且準確無誤成本低地賣給商戶。
涉眾 | 利益訴求 |
---|---|
物料組老闆 | 在準確無誤的情形下,更多更快成本低地將裝置賣給商戶 |
裝置渠道商 | 準確無誤且快速地配送裝置給商戶 |
商戶 | 更快地獲得自己購買的裝置 |
物料運營 | 更加準確的配送裝置給商戶 |
一般而言,涉眾的利益是否被滿足直接決定了軟體產品的成功與否。而分析涉眾利益需要進行詳細的調研,研發同學可以根據產品的調研看到對應的涉眾,及其利益。
業務用例圖
知道了涉眾的利益之後,就要分析業務流程,並對現有的流程進行改進。軟體產品沒誕生之前,業務是如何被處理的,找到原來業務的處理方式則可以梳理出業務用例。
筆者負責的一個業務是向購買裝置的商戶配送裝置,對於業務團隊的實際業務來說,使用者購買裝置有業務價值,業務用例如下:
物流公司和裝置渠道商都是輔助購買裝置的執行者,因此放到右邊。值得注意的是,業務用例要體現價值,雖然在實際業務流程中,商戶同時做了很多事情,比如簽收裝置,但簽收裝置不能反映業務價值,故而只有一個購買裝置的用例。
業務流程分析
瞭解了涉眾的利益並且畫出用例之後,需要分析業務流程,找到我們軟體系統能夠改進的流程片段;完整的業務流程圖可能很龐大,需要關注的是其中最有可能影響涉眾利益的流程片段,如下為購買裝置業務流程中配送裝置的流程片段,該片段不大符合涉眾利益;
可以看到,在原來的業務流程中,配送裝置的流程是在全部業務流程中較為繁重,人肉工作量大的流程片段,不符合涉眾利益;
收集商城訂單資訊不及時,導致配送不及時,影響涉眾的利益 人作為節點參與處理,成本高,耗時長,也是不符合涉眾利益的
所以很明顯,我們的系統需要改進流程,替代人的部分工作
新的流程有效地滿足了涉眾“將裝置更多更快且準確無誤成本低地賣給商戶”的利益訴求。
業務序列圖中,每一個箭頭代表的是職責,在業務序列圖中,需要考慮的是職責的層次問題,過於小的職責放入流程圖中,會導致資訊過載,忽略最有價值的職責。在上圖中,運營核對裝置的配送資訊是一個很重要的職責,在原來的需求中體現比較弱,研發同學可以藉助業務流程的分析來分析需求中不合理的地方,完善需求,避免後期的改動,前期越是完善,後期的損失成本越低。
業務流程分析是一件很複雜的事情,研發同學可以利用需求中的資訊,同時加上自己跟涉眾的日常溝通和調研,把握核心的涉眾利益,業務用例和業務流程,就可以解決大部分在需求上的理解偏差問題。
系統建模
系統建模關注的是系統與外部的邊界和系統自身的職責
系統建模需要做的事情
畫出系統用例 寫出用例規約
系統用例圖
系統用例圖是業務流程中,系統執行者與系統發生的有價值的互動。系統執行者可以是人,可以是外部系統,甚至可以是時間。系統用例要體現系統的價值,系統會做很多事情來實現業務價值,我們應當關注業務價值。有些是低層次的職責,沒有體系具體價值,如:“獲取商城訂單資訊”是為了配送訂單中的裝置而發生,應當關注“配送裝置”。
如下是倉配系統的系統用例圖:
系統用例規約
有了業務流程圖和系統用例圖,需要根據進一步細化系統邊界上的約束,保證系統的穩定性。系統執行者與系統的互動細化了詳細的約束,系統的穩定性才能提高,如果沒有仔細列出約束,有可能會忽略一些邊界條件,導致系統的故障;如:倉配系統不考慮來自第三方商城訂單要配送的裝置數量限制,則會因為第三方商城出現的錯誤,導致資產損失。
系統約束來源於系統用例,根據業務的規則,詳細地描述了業務流程中的基本路徑,擴充套件路徑和約束。
配送裝置:
系統每小時向第三方商城查詢待配送的訂單 系統驗證訂單是否已經配送 系統驗證訂單要配送的 SKU 是否合法 驗證訂單中配送的裝置數量是否超過最大限制 1000 筆 系統向物流系統請求給訂單中的使用者配送訂單中的裝置
因為步驟 2,3,4 還有其餘可能的路徑,稱之為擴充套件路徑。
訂單已經配送 系統忽略該訂單
這裡的約束不是告訴研發同學如何實現功能,這裡的約束是業務規則,釐清系統執行者與系統之間的邊界,以及邊界上的約束。設計評審的時候,可以關注關鍵路徑上的安全規則是否到位,這麼做對提高系統的安全穩定有極大的幫助。
類的分析與設計
這可能是大多數研發同學比較熟悉的領域,經典的設計模式,類之間的關係,泛化,組合等。但是類從哪裡來呢?是從需求之中憑空產生?又或者突然靈光一閃,有了類的雛形?對類的進行設計與分析之前,需要做的是找到他
識別類
經歷過業務流程,系統建模,我們終於來到了系統裡面,來尋找類。我們所熟知的類有三種,邊界類,控制類和實體類。邊界類是外部系統在系統內部的對映,藉由邊界類,系統和外部系統互動。所以一些介面請求,輸入輸出都屬於邊界類的職責。在倉配系統中,商城就是一個邊界類,將外部系統轉移到內部系統來,遮蔽了介面請求相關的細節。控制類往往是體現用例流程,一般而言,一個用例就是一個控制類。實體類則是系統的核心,實體類良好設計能夠提高系統的複用程度,減低系統的複雜性。
找實體名詞
知道了有這三個類還是不足夠我們識別具體的類,識別具體的類需要去業務流程,系統流程,系統規約中經常出現的名詞。在上面的流程圖中,訂單,商城,裝置,物流,使用者是反覆出現的名稱,說明這些類必然存在。
找到這些業務實體,就是找到類的第一步。
找到屬性
類的屬性也不是憑空產生的,需要對業務實現有價值,使用者不一定有姓名,在物流上下文中,使用者的屬性就只有 ID,收貨地址。找到那些對於系統實現必不可少的屬性,放到正確的類中。如倉配系統中的訂單,包含訂單號,商品,使用者。使用者則有收件地址。
在倉配系統中,使用者只有一個地址,在商城的系統中,使用者則有多個地址,充分說明了,不同的上下文中,類的屬性不是固定的。
找職責
從業務規則和約束中,可以找到一些實體應當有的職責,如訂單,就有驗證合法性的職責。
有時候,有些物件看起來資訊很富裕,但是卻沒有什麼職責,說明他是一個值物件,像上圖中的使用者和收件地址,我們不關心他的 id,只關心收件地址,收件地址就代表著這個使用者。
狀態機
找到類和對應的職責,對於一些主要的實體類,還需要設計出他的狀態機,清晰的狀態機能有效地釐清系統內的一些事件和狀態,增強系統整體的健壯性。
倉配中的訂單,從使用者購買的待發貨狀態,到通知物流發貨,再到實際發貨,物流簽收有一些列狀態的演變。
5 總結
在多人協作的專案中,不斷提高專案質量,除了依靠程式碼之外的工程手段,還要依靠設計建模。
從具體實踐的角度來看,設計建模在不同的環境中,調整具體的流程和側重具體的節點,也能夠實現快速高效,不會導致繁瑣和低效能的現象。
在寫程式碼之前應該做的幾件事情:
找準涉眾利益(越是新的專案,越是要分析好,如果是小功能的迭代,則可以從產品需求文件中尋找); 畫出原來的業務流程圖,和改進之後的業務流程圖(業務流程圖是對業務理解是有極大幫助,在絕大部分場景中都不應該省略); 分析系統的職責邊界,畫出系統用例(往系統中新增較小的功能可以考慮不畫出來,心中有數即可); 寫出具體的用例路徑和約束(對系統安全和穩定越是關注,越應該去寫出具體路徑和約束); 識別主要的類,屬性和職責,畫出重要實體的狀態機(簡單功能則直接用程式碼來表達即可)。
想和一群喜歡折騰與思考的同學一起提升嗎?來微信支付吧,這裡鼓勵思想的碰撞與應用,這裡有海量的資料,有令人激動的業務場景,有各有所長的優秀夥伴,快來一起玩耍吧。
參考文獻:
《軟體方法》 《軟體建模與設計》
來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/31559354/viewspace-2704267/,如需轉載,請註明出處,否則將追究法律責任。
相關文章
- 我們在編寫python程式碼時應該注意那幾件事!Python
- 找工作時,我們應該思考的幾件事情。
- 學習swoole之前,你需要知道的幾件事
- [Flutter翻譯]開始使用Flutter Web之前應該知道的7件事FlutterWeb
- 高能預警:2019年程式設計師最應該做這8件事!!程式設計師
- 寫專案程式碼之前必須要做的事
- 程式碼規範之前端編寫碼規範前端
- 2021年做資料分析需要關注的幾件事
- 我在阿里寫程式碼學會的六件事阿里
- 我們應該如何編寫高質量的前端程式碼前端
- 程式設計師懵逼時刻:幾個月後,之前自己寫的程式碼也看不懂了?程式設計師
- 建立維基百科詞條之前應該瞭解的幾點知識
- 訂單交易平臺二(寫程式碼之前的準備工作)
- 自媒體短影片應該如何做選題?寫好影片指令碼?指令碼
- 富貴教你寫程式碼之前端早下班系列(一)前端
- IT安全專業人員應該知道的12件事
- 應聘遊戲策劃之前,應該做些什麼?遊戲
- 寫程式碼做副業月入10K+的方法都藏在這幾個公眾號
- MySQL備份指令碼,應該這麼寫MySql指令碼
- 在Kubernetes上部署應用時我們常忽略的幾件事
- 改善網路視訊直播系統的效能和程式碼質量,應該怎麼做?
- 幾月份應該吃哪裡的水果?
- 關於CORS 應該注意的幾點CORS
- 開發網校原始碼時應該注意的幾個問題原始碼
- 專案經理應該知道的97件事 --譯者序
- 熱門盤點:企業該如何對待低程式碼?應不應該選擇低程式碼?
- 幾百行程式碼寫個Mybatis,原理搞的透透的!行程MyBatis
- 寫碼時應該縮排使用 tab 還是空格?
- 關於大資料你應該瞭解的五件事兒大資料
- 作為軟體工程師你應該知道的100件事 - Harish軟體工程工程師
- 《Offer一籮筐》求職之前你必須知道的 4 件事!!求職
- 幾道JS程式碼手寫題以及一些程式碼實現JS
- 做教程自媒體應該怎麼做?運營自媒體這幾個步驟來教你
- 我的 2018 幾件事兒 | 掘金年度徵文
- 6 件你應該用 Emacs 做的事Mac
- 重構程式碼(應如寫詩)
- 開始一個新專案前,應當想清楚的幾件事兒
- 精讀《不再需要 JS 做的 5 件事》JS