Skip to content

py-test abstract classes

py-test abstract classes

In certain scenarios comes a need to create abstract classes. Those can be usefull as base classes, to provide a layout for different implementions of inheriting concrete versions. Class is called abstract when it contains at least one abstract method. Such a method simply lacks implementation, just provides a declaration. Due to that, abstract classes cannot be instantiated. So a question arrises – how to unit test their functionality, with python, without the ability to create instances?

Contents

HOW TO

One may ask, why to even test abstract classes, as their aim is to be inherited. First of all, abstract classes can contain some non-abstract methods, and those are the ones that we can test. Secondly, testing abstract classes does not assume not testing inheriting classes. One still should validate whether concrete classes are written correctly. Especially that while inheriting, we can also change implementation of a concrete method from the base abstract class.

One way to approach the unit tests topic in python is to simulate concrete implementation of an abstract base class, by creating a dummy class. Let’s consider 2 scenarions – testing of an independent and dependent concrete method. In both cases, abstract base class is defined using ABC library.

 

1. Testing of a independent method.

 

Consider following abstract class. It contains one abstract and one concrete method:

To test the concrete one, let’s create a Dummy inheriting class, by providing a definition for abstract_hello() method. By not specifying concrete_hello(), we assume the default definition of this method:

Now we can use this dummy class to test concrete_hello() method. I am using pytest library.

This helps us determine that “default” provided method implementation works as expected. That is especially useful if such a logic is more complex. Or in a case where we would like to show how we intend this method to be used in inheriting classes. Of course it is a good practice to validate this method regardless whether subclass implements it differently or not. So let’s consider a concrete class this time:

And test both methods:

 

2. Testing of a dependent method.

 

Now let’s change the implementation of the base class to make concrete method dependent on the abstract one:

In such a case testing of the concrete_hello() is very much dependent on the abstract method implementation. Let’s provide the dummy, not disturbing the logic:

Our test can only follow the same logic:

However this time it is more clear why we should retest this method in every subclass. That is because outcome of the concrete method very much depends on the abstract method and hence will be different for each implementation.

 

Testing abstract classes may seem as an overhead, as we should either way test thoroughly all derived subclasses. However if such a base class is to be used to constantly add new implementations, it is a good practice to validate all default implementations. By providing dummy instances, we can unit test methods in a relatively simple manner.

Leave a Reply

Your email address will not be published. Required fields are marked *