简体   繁体   English

检查两个不同的方法是否在模拟对象上调用了相同的方法

[英]Check that two different methods call the same methods on mocked object

I am using Moq as a mocking framework.我使用 Moq 作为模拟框架。 I have a situation where I want to execute two different methods, that both call methods an an interface.我有一种情况,我想执行两种不同的方法,这两种方法都调用方法和接口。 I want to make sure, that both methods call exactly the same methods on my interface, in the same order and with the same parameters.我想确保这两种方法在我的界面上以相同的顺序和相同的参数调用完全相同的方法。 To illustrate, here is the code:为了说明,这里是代码:

[TestMethod]
public void UnitTest()
{
var classToTest = new ClassToTest();
Mock<IMyInterface> mock1 = new Mock<IMyInterface>();
// Setup the mock
Mock<IMyInterface> mock2 = new Mock<IMyInterface>();
// Setup the mock


classToTest.MethodToTest(mock1.Object);
classToTest.DifferentMethodToTest(mock2.Object);

// here I need help:
mock1.Verify(theSameMethodsAsMock2);
}

For example, if IMyInterface had two methods, Method1(int i) and Method2(string s) , the test should pass if MethodToTest has the structure例如,如果IMyInterface有两种方法, Method1(int i)Method2(string s)测试应该通过如果MethodToTest具有以下结构

void MethodToTest(IMyInterface x)
{
x.Method1(42);
x.Method2("example");
x.Method1(0);
}

and DifferentMethodToTest looks like that:DifferentMethodToTest看起来像这样:

void MethodToTest(IMyInterface x)
{
int a = 10 + 32;
x.Method1(a);
string s = "examples";
x.Method2(s.Substring(0, 7));
x.Method1(0);
// might also have some code here that not related to IMyInterface at all, 
// e.g. calling methods in other classes and so on
}

Same order, same methods, same parameters.同样的顺序,同样的方法,同样的参数。 Is this possible with Moq?这可以用起订量吗? Or do I need another mocking framework?还是我需要另一个模拟框架?

I found a solution by myself which uses InvocationAction :我自己找到了一个使用InvocationAction的解决方案:

[TestMethod]
public void Test()
{
var classToTest = new ClassToTest();

var methodCalls1 = new List<string>();
var invocationAction1 = new InvocationAction((ia) =>
{
     string methodCall = $"{ia.Method.Name} was called with parameters {string.Join(", ", ia.Arguments.Select(x => x?.ToString() ?? "null"))}";
     methodCalls1.Add(methodCall);
});
Mock<IMyInterface> mock1 = new Mock<IMyInterface>();
mock1.Setup(x => x.Method1(It.IsAny<int>())).Callback(invocationAction1);
mock1.Setup(x => x.Method2(It.IsAny<string>())).Callback(invocationAction1);

// Same for mock2 ...


classToTest.MethodToTest(mock1.Object);
classToTest.DifferentMethodToTest(mock2.Object);

CollectionAssert.AreEqual(methodCalls1, methodCalls2);
}

I know that the code is very clumsy, especially the string comparisons, but it's sufficient for the time being.我知道代码很笨拙,尤其是字符串比较,但暂时足够了。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM