Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to use moq to test a concrete method in an abstract class?

In the past when I wanted to mock an abstract class I'd simply create a mocked class in code that extended the abstract class, then used that class in my unit testing...

public abstract class MyConverter : IValueConverter
{
    public abstract Object Convert(...);

    public virtual Object ConvertBack(...) { ... }
}

private sealed class MockedConverter : MyConverter { ... }

[TestMethod]
public void TestMethod1()
{
    var mock = new MockedConverter();

    var expected = ...;
    var actual = mock.ConvertBack(...);

    Assert.AreEqual(expected, actual);
}

I want to get into the habit of using Moq instead. I'm not sure how I'd go about using Moq to test the default return value of my abstract class. Any advice here?

like image 936
michael Avatar asked Oct 07 '11 19:10

michael


People also ask

Can we have concrete methods in abstract class?

No. Abstract class can have both an abstract as well as concrete methods. A concrete class can only have concrete methods. Even a single abstract method makes the class abstract.

Can we mock abstract class using Moq?

Getting started with MoqMoq can be used to mock both classes and interfaces. However, there are a few limitations you should be aware of. The classes to be mocked can't be static or sealed, and the method being mocked should be marked as virtual. (Note there are workarounds to these restrictions.

How can you use concrete methods of an abstract class in Java?

If we want to execute those concrete methods create an instance(object) of the class and call to that specific method. If you declare an abstract method in a class then you must declare the class abstract as well. you can't have an abstract method in a concrete class.


Video Answer


2 Answers

If you set CallBase to true, it will invoke the base class implementation.

var mock = new Mock<MyConverter> { CallBase = true };

See the Customizing Mock Behavior Customizing Mock Behaviour section of the Quick Start.

Invoke base class implementation if no expectation overrides the member (a.k.a. "Partial Mocks" in Rhino Mocks): default is false.

like image 141
Jeff Ogata Avatar answered Oct 25 '22 09:10

Jeff Ogata


You can setup a Mock on an abstract class just like on an interface. In order to test the abstract implementation you need to set the mock object to call the base method for any functions not defined:

var mock = new Mock<MyConverter>();
mock.CallBase = true;
Assert.AreEqual(expected value,mock.Object.ConvertBack(...));
like image 27
Scott Avatar answered Oct 25 '22 10:10

Scott