Java Testing – Should Helper Methods Be Separated from Test Classes?

javatesting

When testing, sometimes a helper method can be useful for repeated task e.g. in test setup.

Concrete example:
We have certain tests against our rest interface using Spring's RestTemplate. To make it easier, the requests are sent with the help of a helper method (let's call it method A() for now), which returns the objects from the response.

This helper method A() seems to pollute the test class, as it is a method which is actually not a test itself. Having multiple helper methods in a test class has a negative effect regarding the overview.

Is it acceptable to create a second class next to the test class, which is containing all helper method? What would be the difficulties if doing so? Or are there any other ways to keep a good overview of the test class?

  • MyTestClass -> containing only methods which are a actuall test
  • MyTestClassUtil -> containing all helper methods that are used by MyTestClass

Best Answer

Is it acceptable to create a second class next to the test class, which is containing all helper method?

Not with all helper methods, but with helper methods that are used in more than one test class.

Design your tests the same way as you implement business classes!

Refactor code duplicates within a class into a local method. If the method is used in different test classes move it into a different test helper class that is used by different tests.

So my OrderTests class has a local method assertEqual(String message, IOrder expected, IOrder actual) and my helper TestDataFactory has a static method createTestOrder() that is used in OrderTests, PriceCalculationTests, PaymentTests, DeliveryTests.

A test may use one or more of the standard factory methods and modifies it as needed. Example:

DeliveryTests.executeOrderWithNoDeliveryAdressShouldThrow() {
    // a valid standard order with one article, user, deliveryadress, ...
    Order sut = TestDataFactory.createTestOrder(); 
    sut.setDeliveryAdress(null); // implements "WithNoDeliveryAdress"

    try {
        sut.execute(); // this should throw
        Assert.fail(); // this should never be reached because of exception.
    } catch(OrderNotCompleteException) {
    }
}
Related Topic