Moq fake one method but use real implementation of another

怎甘沉沦 提交于 2019-12-03 14:25:29

问题


Given an interface IService that has Method1() and Method2().

I want to test that when Method1() throws an Exception, Method2() is called and returns a given value.

(Method2() is called when Method1() throws).

Therefore I need to test a real Method2() with a fake Method1(), they are methods of the same interface.

Here is my test code:

MBase sut.MethodX() is the only entry point. It uses IService.

My aim is to assert that Method2() returns something.

// Arrange
// Fake bytes in.
var networkStreamMock = new Mock<INetworkStream>();
networkStreamMock.Method1(x => x.Read(It.IsAny<byte[]>(), It.IsAny<int>(), It.IsAny<int>())).Returns(It.IsAny<byte[]>());

// Force throw TimeoutException.
var mock = new Mock<IService>();
mock.Setup(x => x.Method1(new Message
{ 
    Xml = Xml,  
}
)).Throws<TimeoutException>();

// Check Method 2 is called. (this is done in its own test so commented out)
// mock.Setup(m => m.Method2(It.IsAny<Message>())).Verifiable();

// New MBase.
IKernel kernel = new StandardKernel(new FakeBindings());
kernel.Rebind<IService>().ToConstant(mock.Object);
MBase sut = kernel.Get<M>();

// Act
sut.MethodX(networkStreamMock.Object);

// Here I would like to assert on the return value of Method2
mock.Verify(m => m.Method2(It.IsAny<Message>()));

Is this possible with Moq or another mocking framework? How do I do it? I can create a manual mock with a fake implementation of Method1() and a real implementation of Method2() but I wonder if there is a better approach.

I have already tested IService in isolation but I now wish to test it's interaction with MBase.


回答1:


You can do this with:

var mock = new Mock<MyNetworkStream>(){ CallBase = true };
mock.Setup(m => m.Method1....

The above code will use the real implementation of MyNetworkStream for any method/property which is not explicitly setup. I.e. it'll call the real Method2(), while the Method1() will be the mocked version.

CallBase=true is usually meant to test abstract classes (if this is right or wrong, is out of the scope of this question).




回答2:


In this case (unless there's a lot more going on) I would just create my own test class extending the class with the real behavior, that implements the interface you need to mock. This way you can mock the one value, and fallback to the base class for the real functionality.



来源:https://stackoverflow.com/questions/19054563/moq-fake-one-method-but-use-real-implementation-of-another

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!