Java · Intermediate level

Intermediate level · Module 5: Unit Testing with JUnit 5 · Lesson 2 of 3

Testing Edge Cases and Exceptions

Test boundaries and error paths, check that exceptions are thrown, and remove duplication with @BeforeEach and parameterized tests.

In this lesson you will

  • Use assertThrows to test error handling
  • Write parameterized tests for several inputs

Key concepts

boundary valueassertThrows@BeforeEach@ParameterizedTest

The lesson

Most bugs hide at the edges: zero, one, the maximum allowed, just above the maximum, empty input. If a member may borrow three books, test two, three and four.

assertThrows(LoanLimitException.class, () -> service.lend(member, book)) passes only if the code throws that exception. It proves that rules are enforced, not just that the happy path works.

@BeforeEach runs before every test, so shared setup lives in one place. @ParameterizedTest with @ValueSource or @CsvSource runs one test method with many inputs, which keeps boundary testing short and readable.

Step by step

  1. Move repeated setup into an @BeforeEach method.
  2. Test the loan limit at 2, 3 and 4 books.
  3. Use assertThrows for the fourth loan.
  4. Rewrite the boundary tests as one parameterized test.

Practice activity

Write tests for every rule of the loan service, including all boundaries and every custom exception.

Expected result: Each rule has a passing and a failing case, and every custom exception is tested with assertThrows.

Check your understanding

  1. What does assertThrows check?

    Show answer

    That running the given code throws the expected type of exception.

  2. If a limit is three, which values should you test?

    Show answer

    Values just below, at and above the limit: two, three and four.

Taught live by an instructor — online or in person. Free course lessons are for self-study and do not lead to a certificate — see registration options.