How to test a new feature

This tutorial uses Spring PetClinic with Cover Plugin for IntelliJ, to demonstrate using Cover Plugin to create tests for a new feature. Please start with the following steps:

  • git clone https://github.com/Diffblue-benchmarks/Spring-petclinic

  • cd Spring-petclinic

  • git checkout a-test-new-feature

  • Open your project in IntelliJ.

  • Navigate to the OwnerController class.

We are going to add a new method to OwnerController that counts the number of dogs belonging to an owner:

class OwnerController {

   /**
   * Counts the number of dogs belonging to the given owner.
   * @param owner The owner
   * @return The number of pets of type "Dog" belonging to the given owner
   */
  public long countDogs(Owner owner) {
       return owner.getPets().stream()
        .filter(pet -> pet.getName().equals("Dog"))
        .collect(Collectors.counting());
  }
}

Let's review the tests which have been created:

  • There’s a test for an owner that doesn’t have any pets, hence it doesn’t have any dogs either. This looks correct.

  • Then we have a test that has a pet that is a dog with the name Bella, but countDogs returns 0. This isn't right.

@Test
public void testCountDogs3() {
  Pet pet = new Pet();
  LocalDate birthDate = LocalDate.ofEpochDay(1L);
  pet.setBirthDate(birthDate);

  Owner owner = new Owner();
  owner.setLastName("Doe");
  owner.setId(1);
  owner.setCity("Oxford");
  owner.setAddress("42 Main St");
  owner.setFirstName("Jane");
  owner.setTelephone("4105551212");
  pet.setOwner(owner);

  pet.setId(1);
  pet.setName("Bella");

  PetType petType = new PetType();
  petType.setId(1);
  petType.setName("Dog");
  pet.setType(petType);

  HashSet<Pet> petSet = new HashSet<Pet>();
  petSet.add(pet);
  owner.setPetsInternal(petSet);

  assertEquals(0L, this.ownerController.countDogs(owner));
}
  • The last test has two pets that are both dogs, but countDogs returns 0 again. So, this is incorrect too.

Reviewing these candidate tests reveals unintended behaviour. We now need to modify the tests to match the expected behaviour, and then find the bug that has caused this.

  1. Modify the assertions so that they have the expected behaviour, i.e. one dog means countDogs returns 1, two dogs means countDogs returns 2. The corrected test will now fail when we run it.

  2. To find the bug in our implementation, we can put a breakpoint into one of the failing tests and run the test With Debugging and step through our implementation.

  3. This helps us find that the filter is wrong: we compare the name of the pet (getName()) instead of the name of the type of the pet (getType().getName()).

Fix this bug before running the test again, to check that the fix is actually correct. The tests should now pass.

Diffblue Cover does not add a duplicate test if exactly the same test already exists.

The diagram below shows our journey through this tutorial:

Last updated