0

I'm trying to write a unit test for an abstract class. More specifically, I have a class like

public abstract class MyAbstractClass
{
    // ... 
    private Something _myPrivateVariable; 
    // ...
    protected void MyProtectedMethod(string[] names) { // ... }
    // ... 
}

and I want to call MyProtectedVoid with parameters and then verify that _myPrivateVariable was set to a particular value.

I know how to invoke a private method of an instance of a class using GetMethod like in How do I use reflection to invoke a private method?, but I don't know how to do this type of thing with an abstract class considering that I can't create an instance of it.

Community
  • 1
  • 1
  • Have you tried mocking it i.e with RhinoMocks? Example: http://stackoverflow.com/questions/6960459/rhino-mock-an-abstract-class-w-o-mocking-its-virtual-method – MistyK Jan 27 '17 at 22:55
  • You should not check private variable in UT. Check http://stackoverflow.com/questions/1093020/unit-testing-and-checking-private-variable-value and many others. – qxg Jan 28 '17 at 01:40

2 Answers2

0

Suppose Caller is the class that is trying to call your protected method from abstract class. In this case, you will have to inherit abstract class, since it will not allow you to create a new instance of it:

public abstract class MyAbstractClass
  {
    // ... 
    private Something _myPrivateVariable; 
    // ...
    protected void MyProtectedMethod(string[] names) { // ... }
    // ... 
  }

public class Caller:MyAbstractClass // inheriting the abstract class
 {
     public void GetAbstractMethod(){
     MyProtectedMethod(/*string[] values*/);
     } 
  }
Coke
  • 965
  • 2
  • 9
  • 22
0

You can't call a method of a object that doesn't exist, and abstract classes, by themselves, can't be created.

But you're actually trying to solve a fairly simple problem. Because you just want to test the methods of the abstract class you can create a test class that inherits from the abstract class and "implements" any abstract methods by failing the test. You can then use the test class to test abstract class and its protected methods and fields.

public class MyAbstractTestClass : MyAbstractClass
{
    public void TestProtectedMethod(string[] names)
    {
        Assert...
        this.MyProtectedMethod(names);
        Assert...
    }
}

This lets you call the routines, gives you access to protected methods and fields, and because you declare the test class in your unit tests you don't affect other code. This approach will even catch some cases where the abstract base class changes without updating the test code.

Ray Fischer
  • 936
  • 7
  • 9