Powerful abstract protected method

I have an abstract class:

public abstract class MyClass
{
    protected abstract bool IsSavable();

    protected bool IsExecutable()
    {
        //New mode or edit mode
        if (ViewMode == ViewMode.New || ViewMode == ViewMode.Edit)
        {
            return IsSavable();
        }

        //Search mode
        if (ViewMode == ViewMode.Search)
        {
            return true;
        }

        return false;
    }
}

      

I would like to unit test this class. So I need to mock the "IsSavable" method. It should always return "true".

I know how to mock my abstract class with Moq. But how can I mock my abstract protected method so that it returns true?

The IsSavable function is called in my abstract class on a specific method (IsExecuteable). I would like to test this method. I know that most of you would recommend testing as in a class that implements "IsSavable". Unfortunately, this will be a lot of classes, and I would like to test my IsExecutable method only once.

+3


source to share


3 answers


I would like to unit test this class. So I need to mock the "IsSavable" method. It should always return "true".

No, this is non-sequitur. You can simply create a subclass that does what you want:

// Within your test code
class MyClassForTest : MyClass
{
    // TODO: Consider making this a property 
    protected override bool IsSavable()
    {
        return true;
    }
}

      



Then when you want to run your test, instantiate MyClassForTest

instead MyClass

.

Personally, I prefer to use mocking dependency frameworks rather than the classes I'm testing.

+8


source


Just to confirm what @Jon says - the fact that you are trying to Mock a protected method AND call another protected method on an abstract class indicates a smell.

But, by pulling out the heavy artillery - MoqProtected()

extensions and again using direct reflection to actually trigger the SUT IsExecutable

, you can actually do what you want:



// Arrange
var mockMyClass = new Mock<MyClass>();
mockMyClass.Object.ViewMode = ViewMode.New; // I've made an assumption or two here ...
mockMyClass.Protected().Setup<bool>("IsSavable").Returns(true);

// Act!
var result = (bool)mockMyClass.Object.GetType().InvokeMember("IsExecutable",
    BindingFlags.InvokeMethod | BindingFlags.NonPublic | BindingFlags.Instance,
    null,
    mockMyClass.Object,
    null);

// Assert
Assert.IsTrue(result);
mockMyClass.Protected().Verify<bool>("IsSavable", Times.Once());

      

But I personally would like to revise the constructive and technological ties at this stage.

+2


source


The fastest thing to do is to inherit from "MyClass" and override IsSavable.

In a test, it can be a little trickier to distinguish the under test, but that does the trick.

Also, you might think about design - maybe there should be two classes -> one for Saveable behavior and one for unSavable?

+1


source







All Articles