Junit4 异常测试

1 概述

在本指南中,我们将学习如何测试具有意外条件的方法引发的异常。

2 JUnit 4异常测试示例

有三种方法可以处理异常。
  • 预期的异常
  • ExpectedException规则
  • Try/Catch Idiom

2.1 预期的异常

您如何验证代码是否按预期抛出异常?验证代码能否正常完成很重要,但是确保代码在异常情况下的行为也很重要。例如:
new ArrayList<Object>().get(0);

此代码应引发IndexOutOfBoundsException。该 @Test 标注有一个可选的参数“ expected”那需要为值的子类 Throwable。如果我们想验证 ArrayList 抛出正确的异常,我们将编写:

@Test(expected = IndexOutOfBoundsException.class) 
public void empty() { 
     new ArrayList<Object>().get(0); 
}

该 expected 参数应谨慎使用。如果 方法中的任何代码抛出 ,上述测试将通过 IndexOutOfBoundsException。对于更长的测试,建议使用以下 ExpectedException 规则。

更深入地测试异常
上述方法在简单情况下很有用,但有其局限性。例如,您不能测试异常中消息的值,也不能测试引发异常后域对象的状态。

2.2 Try/Catch Idiom

为了解决这个问题,您可以使用JUnit 3.x中流行的try / catch习惯用法:
/**
 * 一点教程网: http://www.yiidian.com
 */
@Test
public void testExceptionMessage() {
    try {
        new ArrayList<Object>().get(0);
        fail("Expected an IndexOutOfBoundsException to be thrown");
    } catch (IndexOutOfBoundsException anIndexOutOfBoundsException) {
        assertThat(anIndexOutOfBoundsException.getMessage(), is("Index: 0, Size: 0"));
    }
}

2.3 ExpectedException规则

或者,使用 ExpectedException 规则。通过此规则,您不仅可以指示期望的异常,还可以指示期望的异常消息:
/**
 * 一点教程网: http://www.yiidian.com
 */
@Rule
public ExpectedException thrown = ExpectedException.none();

@Test
public void shouldTestExceptionMessage() throws IndexOutOfBoundsException {
    List<Object> list = new ArrayList<Object>();
 
    thrown.expect(IndexOutOfBoundsException.class);
    thrown.expectMessage("Index: 0, Size: 0");
    list.get(0); // execution will never get past this line
}

ExpectMessage还允许您使用Matchers,这使您的测试更具灵活性。一个例子:

thrown.expectMessage(CoreMatchers.containsString("Size: 0"));

此外,您可以使用Matchers检查Exception,如果该异常具有要验证的嵌入状态,则很有用。例如

import static org.hamcrest.Matchers.hasProperty;
import static org.hamcrest.Matchers.is;
import static org.hamcrest.Matchers.startsWith;

import javax.ws.rs.NotFoundException;
import javax.ws.rs.core.Response;
import javax.ws.rs.core.Response.Status;

import org.junit.Rule;
import org.junit.Test;
import org.junit.rules.ExpectedException;
/**
 * 一点教程网: http://www.yiidian.com
 */
public class TestExy {
    @Rule
    public ExpectedException thrown = ExpectedException.none();

    @Test
    public void shouldThrow() {
        TestThing testThing = new TestThing();
        thrown.expect(NotFoundException.class);
        thrown.expectMessage(startsWith("some Message"));
        thrown.expect(hasProperty("response", hasProperty("status", is(404))));
        testThing.chuck();
    }

    private class TestThing {
        public void chuck() {
            Response response = Response.status(Status.NOT_FOUND).entity("Resource not found").build();
            throw new NotFoundException("some Message", response);
        }
    }
}

3 结论

在本指南中,我们学习了如何测试方法引发的异常。

热门文章

优秀文章