最近
工作上的活就是研究一下如何為一個(gè)歷史代碼工程添加
單元測(cè)試,已經(jīng)做完了,就想拋磚引玉和大家分享一下結(jié)果,聽聽大家的反饋。
該工程目前還是VS2010下的C#代碼,雖然大量使用了繼承,封裝和多態(tài),但對(duì)接口的應(yīng)用非常少,所以基本上沒辦法用常見的Mock框架(如Moq, Rhino Mock,等)來寫單元測(cè)試。
考慮下來,解決方案無非兩種:一是重構(gòu)現(xiàn)有代碼,通過接口(interface)來實(shí)現(xiàn)依賴注入(Dependency Injection, DI);二是尋找無需通過接口直接支持虛擬實(shí)體類的Mock框架,用來攔截對(duì)依賴對(duì)象的訪問,返回預(yù)定的結(jié)果。采用方案一的話,優(yōu)化了代碼架構(gòu),從長(zhǎng)遠(yuǎn)來說更好一些,但是工作量較大,還需要做大量的測(cè)試以保證不會(huì)改變現(xiàn)有代碼功能。采用方案二的話,則不需要對(duì)現(xiàn)有代碼做任何改動(dòng),只需要直接創(chuàng)建測(cè)試代碼就好了。因此方案二還是很有吸引力的,我就按這個(gè)方向做了一些研究。
我發(fā)現(xiàn)市面上暫時(shí)還沒有開源的Mock框架(.NET單元測(cè)試相關(guān))支持虛擬實(shí)體類,而收費(fèi)的我也只找到Microsoft Fakes, TypeMock Isolator和Telerik JustMock這三個(gè)。三者雖然用法上有些差異,但是主要功能比較接近,差別主要體現(xiàn)在以下幾個(gè)方面:
1.從價(jià)格上來看:
Microsoft Fakes,沒有免費(fèi)版,只有在VS2012/VS2013的Premium和Ultimate版中才能用,而我們的開發(fā)環(huán)境用的主要是Professional版的,升級(jí)到相應(yīng)版本的話成本很高(VS2013的話
Windows Store差價(jià)$1770,MSDN Subscription差價(jià)$4920)
Telerik JustMock滿足需求的版本價(jià)格是每個(gè)開發(fā)者$399,包含一年免費(fèi)升級(jí)+支持,(參見Buy JustMock)
TypeMock Isolator滿足需求的版本價(jià)格是$799每個(gè)license,$150每年升級(jí)+支持,(參見Isolator Pricing)
由于Fakes價(jià)格太高,而且還需要升級(jí)現(xiàn)有代碼,我們直接就不考慮了。當(dāng)然如果已經(jīng)在用相應(yīng)版本的話,還是可以考慮的,畢竟
微軟自己的東西還是用起來最方便的。
2.從功能上看,根據(jù)我們的一個(gè)測(cè)試用例分別用TypeMock和JustMock試寫了一下,發(fā)現(xiàn)JustMock更強(qiáng)大一些。 我們的這個(gè)測(cè)試用例是要測(cè)某個(gè)時(shí)間值由于特殊原因不包含年份,因此從客戶端傳到位于不同時(shí)區(qū)的服務(wù)端時(shí),在跨年時(shí)會(huì)被解析到錯(cuò)誤的年份。比如:客戶端位于GMT+8在2014/01/01 07:00:00時(shí)傳了01/01 07:00:00過來,而服務(wù)端位于GMT,當(dāng)時(shí)是2013/12/31 23:00:00,這個(gè)時(shí)間就會(huì)被解析成2013/01/01 07:00:00。解析調(diào)用的是DateTime.ParseExact()方法。TypeMock對(duì)MSCorLib中類的虛擬只提供了有限的支持,不支持這個(gè)方法的虛擬。而JustMock在這方面則做得好一些,能夠支持該方法。
所以,我的最終結(jié)論是要么重構(gòu)代碼,使用接口來實(shí)現(xiàn)依賴注入,那么基本上各種Mock框架都能用;要么就買JustMock,不用動(dòng)現(xiàn)有代碼,直接加單元測(cè)試就好了。