Moq:我可以在模拟的成员/属性行为和未成员的成员/财产行为之间进行交换吗?

时间:2012-03-07 01:08:54

标签: unit-testing c#-4.0 tdd moq moq-3

我想使用我在测试类中使用的模拟库的一个实例,但是,对于某些测试,我可能想要模拟其中一个成员函数来执行/返回模拟行为/返回值;对于其他测试,我可能想要库的未模拟(本机)功能。有没有办法在一个实例中设置Setup(模拟行为),在另一个实例中交换“UNSetup”(unmocked行为)?

2 个答案:

答案 0 :(得分:2)

没有任何内置机制可以做到这一点,但部分模拟让你做同样的事情(有一些限制)。 Parial mock 允许您模拟接口的具体实现,而不是单独的接口,如下所示:

var partialMock = new Mock<ServiceImplementation>();

限制是您可能想要模拟的所有方法都需要是虚拟的,否则Moq无法拦截它们:

public class ServiceImplementation
{
    public virtual int SomeMethod()
    {
        return 5;
    }

    public virtual int SomeOtherMethod()
    {
        return SomeMethod()*2;
    }
}


var partialMock = new Mock<ServiceImplementation>();
// we stub one method
partialMock.Setup(m => m.SomeMethod()).Returns(3);
// and use other's real implementation
var value = partialMock.Object.SomeOtherMethod();

问题当然在于虚拟;如果你不能让你的成员虚拟,这显然是行不通的。虽然有一些小的解决方法 - 使用真正的实现作为存根设置的一部分:

// note we base our stub on interface now
var implementation = new ServiceImplementation();
var mock = new Mock<IServiceImplementation>();
// we call real implementation as part of return setup
mock.Setup(m => m.SomeMethod()).Returns(implementation.SomeMethod());

答案 1 :(得分:1)

怎么样:

MyMock.CallBase = true;

对于任何未设置方法,实际实现都被称为...