Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How should a unit test deal with expected and unexpected exceptions?

Should it pass the test when the expected exception takes place? Should it fail the test when an unexpected exception arises? Is it redundant to handle the exception since it'll fail the test and therefore act as a test?

like image 388
Victor Avatar asked Jun 10 '14 19:06

Victor


2 Answers

Test Expected Exceptions

You have to add the expected attribute with the expected exception, so the test will pass if the specified exception is thrown. Otherwise, it will fail.

For example:

@Test(expected=NullPointerException.class)
public void cannotConvertNulls() {
    service.convert(null);
}

or...

@Test(expected = ArithmeticException.class)  
public void divisionWithException() {  
    int i = 1/0;
}

Documentation says:

The Test annotation supports two optional parameters. The first, expected, declares that a test method should throw an exception. If it doesn't throw an exception or if it throws a different exception than the one declared, the test fails.

Test Timemouts

Just to let you know, you can also test timeouts.

The second optional parameter, timeout, causes a test to fail if it takes longer than a specified amount of clock time (measured in milliseconds). The following test fails:

@Test(timeout=100) 
public void infinity() {
   while(true);
}

Hope to help

like image 175
Federico Piazza Avatar answered Oct 03 '22 21:10

Federico Piazza


For expected exceptions there are really nice ways to do this with JUnit:

@Test(expected=NullPointerException.class)
public void testNullPointerExceptionIsThrown() {
    ArrayList emptyList;
    emptyList.size(); //or add, remove etc. 
}

The above test in JUnit would pass because it was declared with the @Test annotation that the test method should expect that a null pointer exception is thrown.

like image 42
Force444 Avatar answered Oct 03 '22 21:10

Force444