我正在尝试使用Moq来模拟接口,但是我看不到该怎么做。该界面如下所示:
public delegate void MyDelegate(int i);
public interface MyInterface
{
void Method(int i);
MyDelegate MyDelegate { set; }
}
Run Code Online (Sandbox Code Playgroud)
我正在测试将带有此接口的对象作为依赖项的组件。我希望能够在调用该方法时测试在引发委托的情况下的交互,但是我看不到该怎么做。我知道这是设计界面的一种有点奇怪的方法,但是我对此没有控制权。
假设我有一个要测试的类:
class SystemUnderTest
{
int i = 0;
readonly MyInterface myInterface;
public SystemUnderTest(MyInterface myInterface)
{
this.myInterface = myInterface;
this.myInterface.MyDelegate = DelegateHandler;
}
public int Run(int input)
{
this.myInterface.Method(input);
return i;
}
void DelegateHandler(int i)
{
this.i = i;
}
}
Run Code Online (Sandbox Code Playgroud)
我已经尝试过这样的测试,但是在设置模拟时却给出了异常。“ ArgumentException:无法找到附加或分离方法Void set_MyDelegate(ConsoleApp1.MyDelegate)的事件。
static void Main(string[] args)
{
// Arrange
Mock<MyInterface> mock = new Mock<MyInterface>();
mock
.Setup(m => m.Method(It.IsAny<int>()))
.Raises(m => m.MyDelegate = null, 5);
// Act
var sut = new SystemUnderTest(mock.Object);
var result = sut.Run(5);
// Assert
Trace.Assert(result == 5);
}
Run Code Online (Sandbox Code Playgroud)
您可以这样说,SystemUnderTest.DelegateHandler通过MyDelegate局部变量桥接您。尝试这样的事情:
MyDelegate del = null;
var mock = new Mock<MyInterface>();
mock.SetupSet(m => m.MyDelegate = It.IsAny<MyDelegate>())
.Callback<MyDelegate>(d => del = d);
mock.Setup(m => m.Method(It.IsAny<int>()))
.Callback<int>(i => del.Invoke(i));
Run Code Online (Sandbox Code Playgroud)
然后实际上SystemUnderTest.DelegateHandler每次调用时都会调用您的方法mock.Method。