Unit Testing – How to Unit Test Utility Classes

static methodstestingunit testingUtilities

All of us have some utility classes, which contain only static methods, for usage from different sources. Now, there can be two approaches which can be taken towards testing this piece of code.

Approach 1:

Have separate unit tests for utility classes. Wherever they are being called, mock out their interaction using some test framework which has provision for it, such as PowerMock. This essentially treats the utility class as a separate component of the system, which needs to be individually tested out and maintained.

Approach 2:

Do not write unit tests for utility classes. However, tests which are written for your other core classes which interact with this utility class, let that interaction happen, which will intrinsically ensure that the code written in this utility class is properly tested for different usecases. If something breaks, the tests for other components should be able to catch it.

Please share your thoughts on which approach is preferable, or if there is some other manner in which people go about this.

Best Answer

I think there is a big misunderstanding about 'utility' classes out there. Just because you make a class 'static' it does not make it a utility class. If your static utility class has dependencies (which may manifest themselves in other static 'utility' classes), it introduces side effects or its behavior cannot be completely controlled by its inputs is not a utility class.

True utility classes do not need to be mocked because their output is always deterministic depending on their inputs.

Unit testing is about instantiating a small part of your application (a unit) in isolation so you can (potentially) test all code paths within that unit. Mocking dependencies achieves this isolation. If a utility class breaks the isolation, again it is not a utility class because a utility class is supposed to be isolated by definition.

So in an application one should never want to or have to mock utility classes. Classes that you feel need to be mocked need to be turned into first class instantiable classes and need to be passed into the unit as a dependency (See Dependency Injection). These dependencies then can be mocked easily so the unit can be tested in isolation.