[英]How to raise a delegate event using a ref parameter in NSubstitute 3.1?
我正在使用第3方庫的C#項目中。 該庫使用ref參數定義了一個非常不尋常的委托事件:
event GetDataHandler OnGetData;
public delegate bool GetDataHandler(string name, ref byte[] data);
我正在嘗試通過NSubstitute(版本3.1)在單元測試中引發此事件,但是我無法使其正常工作。 我嘗試了這段代碼(基本上我可以想到的每個變體):
var theKey = "test";
byte[] theData = null;
_theObject.OnGetData += Raise.Event<GetDataHandler>(theKey, ref theData);
但這不能編譯。 編譯器說: 參數2可能不能與'ref'關鍵字一起傳遞 。
我知道NSubstitute 4.x的out / ref機制已經更改,但是我的公司尚未升級到較新版本。
有什么辦法可以使用NSubstitute 3.1來啟動和運行它? 非常感謝!
最好的問候,奧利弗
Raise.Event
重載將參數作為params object[]
。 我們可以在此params數組中將byref字節數組作為標准值傳遞(這意味着我們對於傳遞的事件args不會獲得編譯時的安全性,但是如果我們弄錯了,測試會很快地將其提取出來) :)):
_theObject.OnGetData += Raise.Event<GetDataHandler>("name", theData);
這是一個可執行的示例:
using NSubstitute;
using Xunit;
public delegate bool GetDataHandler(string name, ref byte[] data);
public interface ISomeType {
event GetDataHandler OnGetData;
}
public class SampleFixture {
string lastNameUsed = "";
byte[] lastBytesUsed = new byte[0];
[Fact]
public void SomeTest() {
var sub = Substitute.For<ISomeType>();
var data = new byte[] { 0x42 };
sub.OnGetData += Sub_OnGetData;
sub.OnGetData += Raise.Event<GetDataHandler>("name", data);
Assert.Equal("name", lastNameUsed);
Assert.Equal(data, lastBytesUsed);
}
private bool Sub_OnGetData(string name, ref byte[] data) {
lastNameUsed = name;
lastBytesUsed = data;
return true;
}
}
在評論中提供更多信息后進行編輯。
我不認為NSubstitute支持檢查這種情況下返回的值。
在不完全知道您要測試的內容的情況下,我可以建議一些用於測試此類內容的一般方法。
第一種選擇是手工編寫一個可以完全控制的測試雙(本例中為ISomeType
的實現)。 除非接口很大,否則我建議使用這種方法。
另一種選擇是分別測試代表和連線。 例如,給定此類:
public class ClassUnderTest {
public ClassUnderTest(ISomeType dep) {
dep.OnGetData += Dep_OnGetData;
}
public static bool Dep_OnGetData(string name, ref byte[] data) {
data = System.Text.Encoding.UTF8.GetBytes(name);
return true;
}
}
我們可以獨立測試委托,然后測試我們已經將該委托連接起來了:
[Fact]
public void TestDelegate() {
byte[] data = new byte[0];
var result = ClassUnderTest.Dep_OnGetData("hi", ref data);
Assert.True(result);
Assert.Equal(new byte[] { 104, 105 }, data);
}
[Fact]
public void TestWireup() {
var sub = Substitute.For<ISomeType>();
var subject = new ClassUnderTest(sub);
sub.Received().OnGetData += ClassUnderTest.Dep_OnGetData;
}
我認為在這種情況下,委托測試可能非常有用,但是連線測試可能並不好,因為它非常特定於特定的實現,而不是所需的行為/結果。 但是在這種情況下,很難觀察到特定的效果,因此這是一個潛在的答案。
第三,我們也許可以在所討論的庫中使用更具可測試性的包裝器。 或此測試可能完全處於錯誤的級別-警惕我們不擁有的模擬類型。 (我在這里已經寫了一些。)
如果您可以提供更多有關在這種情況下要測試的內容的信息,我們很樂意為您提供一個更合理的答案。 :)
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.