[java] JUnit Testing Exceptions

Though @Test(expected = MyException.class) and the ExpectedException rule are very good choices, there are some instances where the JUnit3-style exception catching is still the best way to go:

@Test public void yourTest() {
  try {
    systemUnderTest.doStuff();
    fail("MyException expected.");
  } catch (MyException expected) {

    // Though the ExpectedException rule lets you write matchers about
    // exceptions, it is sometimes useful to inspect the object directly.

    assertEquals(1301, expected.getMyErrorCode());
  }

  // In both @Test(expected=...) and ExpectedException code, the
  // exception-throwing line will be the last executed line, because Java will
  // still traverse the call stack until it reaches a try block--which will be
  // inside the JUnit framework in those cases. The only way to prevent this
  // behavior is to use your own try block.

  // This is especially useful to test the state of the system after the
  // exception is caught.

  assertTrue(systemUnderTest.isInErrorState());
}

Another library that claims to help here is catch-exception; however, as of May 2014, the project appears to be in maintenance mode (obsoleted by Java 8), and much like Mockito catch-exception can only manipulate non-final methods.