如何模擬資料
在上一篇介紹完BDD以及如何在VSCode撰寫BDD的測試案例以及Step之後,相信大家在撰寫測試案例時時常會遇到相依的介面不知道該如何處理,再來算是知道了Mock,Fake之後也不知道該在測試的程式中怎麼做,所以今天跟大家介紹C#的NSubstitute,可以模擬介面的方法接收參數並且返還資料。
模擬資料
「前輩,昨天提的測試案例我遇到問題了,我要測試的對象有相依元件,我該如何產生這些元件來跟我的測試對象互動。」
一大早小光問大頭關於測試的問題,這時大頭似乎也在寫測試案例上遇到問題。
「恩,我也遇到一些問題,不過我遇到的是我如何驗證沒有回傳值的測試對象,不然我們一起去問老K前備吧。」
所以他們兩個就一起去找老K詢問關於撰寫測試案例時遇到的問題。
「好的,你們遇到的是如何模擬資料來完成你們的測試。不過在告訴你如何做之前先告訴你們一些相關知識,因為這樣以後在說明上會比較方便。」
測試中的名詞
這邊有些測試時的專有名詞要跟大家介紹一下,這是由Martin Fowler的文章TestDouble參考來的,如下表所示。
名詞 | 說明 |
---|---|
SUT | System Under Test 我們要測試的對象 |
DOC | Depended-On Component SUT需要的元件 |
Dummy | 只是用來填充方法的參數,在方法內不會實際被用到 |
Fake | 簡化過的元件提供資訊讓測試可以正常的進行 |
Stubs | 提供SUT資訊來驗證SUT是否有正常運作 |
Spies | 提供SUT資訊,並且監控SUT的行為 |
Mocks | 用來幫助SUT檢查其行為是否被執行 |
在前面的例子中小光遇到的問題可以透過Stubs
來解決而大頭需要過Mocks
來驗證SUT的行為。
NSubstitute
解釋完名詞後,接下來跟大家介紹如何透過工具NSubstitute來處理以上的問題,首先還是先安裝套件,請各位輸入以下指令來安裝。
dotnet add package NSubstitute
而使用方法主要是透過Substitute.For<介面>()
來產生元件,再來透過.Get(Arg.Any<int>()).Return(x => {})
產生模擬的方法。所以整個語法可以看一下下列範例。
var logger = Substitute.For<ILogger<LoginService>>(); // Dummy
var repo = Substitute.For<IUserRepo>();
repo.Get(Arg.Any<int>()).Return(x => { return UserInfo()} ); // Fake, Stubs, Spies, Mocks
var sut = new LoginService(repo, logger);
上面例子簡單的說明如果在LoginService
有需要用到元件時可以透過Substitute來產生元件,並且可以模擬該介面的方法讓測試可以繼續進行下去,又或者可以藉由模擬回傳特定值來驗證SUT的運作是否正常。
後記
今天藉由大頭的案例跟大家介紹如果遇到有相依見面的元件該如何測試,原則上單元測是要專注在受測的元件上,所以通常就以NSubstitute來處理相依的介面,然後依照測試案例來返還受測元件所需的資料藉此驗證受測元件的正確性,此外對於一些測試的名詞介紹可大家可以參考測試中常見的名詞:Stub, Dummy, Mock..等等。