11

When I try to test this method

    static void validatePostcode(final String postcode, final String addressLine)
    {
        if(! hasValidPostcode(postcode, addressLine)) {
            throw new InvalidFieldException("Postcode is null or empty ");
        }
    }

using the following test

    @Test
    public void testThrowsAnException()
    {
        assertThatThrownBy(validatePostcode("", "")).isInstanceOf(InvalidFieldException.class);
    }

I get this error message in IntelliJ

assertThatThrownBy (org.assertj.core.api.ThrowableAssert.ThrowingCallable) in Assertions cannot be applied to (void)

 
Same thing with assertThatExceptionOfType.

Is it possible to test that static method actually throws an unchecked exception using AssertJ? What should I change in my test?

Cybex
  • 481
  • 1
  • 6
  • 29
  • 1
    why would you test it like that? Use an ExpectedException. https://www.baeldung.com/junit-assert-exception – Stultuske Aug 08 '19 at 07:45
  • We use JUnit4 and I know about `@Test(expected = RuntimeException.class)` but was looking to do the same using AssertJ. – Cybex Aug 08 '19 at 07:51
  • 2
    @Cybex don't use `@Test(expected = ...)`. It's basically like wrapping the entire method body in a try/catch, so the test "passes" if *anything* in the test throws that exception, not just the thing you intend to test. So, especially for unchecked exceptions, your test can appear to pass even when it's not doing what you think it does. – Andy Turner Aug 08 '19 at 08:04
  • @Andy Turner, yeah, this is one of the reasons why I want to switch to AssertJ. – Cybex Aug 08 '19 at 09:02
  • 1
    @Cybex but JUnit 4.13 adds [assertThrows](https://junit.org/junit4/javadoc/latest/org/junit/Assert.html#assertThrows(java.lang.Class,%20org.junit.function.ThrowingRunnable)). No need to, ahem, throw the baby out with the bathwater. – Andy Turner Aug 08 '19 at 10:30
  • @Andy Turner Thanks, I'll take a look at it. But I guess for consistency it would be better to stick with one library (AssertJ). – Cybex Aug 08 '19 at 13:29
  • 1
    AssertJ also lets you chain other assertion after `isInstanceOf` like `hasMessage`, see https://assertj.github.io/doc/#assertj-core-exception-assertions-assertThatThrownBy – Joel Costigliola Aug 09 '19 at 14:48

2 Answers2

19

As the compilation error demonstrates, that method expects a throwing callable.

@Test
public void testThrowsAnException()
{
    assertThatThrownBy(() -> validatePostcode("", "")).isInstanceOf(InvalidFieldException.class);
}
Ben R.
  • 1,965
  • 1
  • 13
  • 23
2

change to this way. you need to pass lambda to test with assertj

assertThatThrownBy(()->validatePostcode("","")).isInstanceOf(InvalidFieldException.class);