JUnit:测试某种类型的异常

Sam*_*est 3 java junit unit-testing exception

我想知道我是否可以测试(使用JUnit)异常生成的特定消息被抛出而不仅仅是"是否"抛出异常.例如,JunitTest.java代码实际上将通过测试,因为抛出了异常,但如果我还想测试异常生成的字符串是否等于:"测试异常:整数可能不是负..."这是可能的?

TestException.java

public class TestException extends Exception {  
    /**
     * @param message informative message about the problem found
     */
    public TestException (String message) {
        super("Test Exception: " + message);
    }
}
Run Code Online (Sandbox Code Playgroud)

Test.java

public void function(Integer mustBePositive) throws TestException {
    if (mustBePositive < 0) {
        throw new TestException("Integer may not be negative..");
    }
    else {
        mustBePositive = myNum
    }
}
Run Code Online (Sandbox Code Playgroud)

JunitTest.java

import org.junit.*;

public class JUnitTest {

    @Test(expected = TestException.class)
    public void functionTest() throws TestException {
        function(-1);
    }
}
Run Code Online (Sandbox Code Playgroud)

ass*_*ias 8

注意:我认为@Matthew的答案是优越的.

您可以使用以下结构 - 它测试抛出了正确的异常(TestException.class)并且消息是预期的.

@Test(expected = TestException.class)
public void test_function_negative() {
    try {
        function(-5);
    } catch (TestException ex) {
        assertEquals("Integer may not be negative..", ex.getMessage());
        throw ex;
    }
}
Run Code Online (Sandbox Code Playgroud)

编辑
为什么我重新抛出异常(在评论之后):下面的第一个测试通过,而第二个测试没有.因此它增加了额外的验证层.现在,如果我在下面的代码中捕获了ExceptionB,则两个测试都将失败.

@Test
public void test1() throws ExceptionB {
    try {
        throw new ExceptionA();
    } catch (ExceptionA e) {
        assertEquals("message", e.getMessage());
    }
}

@Test(expected=ExceptionB.class)
public void test2() throws ExceptionA {
    try {
        throw new ExceptionA();
    } catch (ExceptionA e) {
        assertEquals("message", e.getMessage());
        throw e;
    }
}

public class ExceptionA extends Exception{
    @Override
    public String getMessage() {
        return "message";
    }
}
public class ExceptionB extends ExceptionA{}
Run Code Online (Sandbox Code Playgroud)


Mat*_*ell 6

您可以使用标准的JUnit TestRule ExpectedException.这允许您测试抛出异常,并测试异常附带的消息.例如:

public static class HasExpectedException {
  @Rule
  public ExpectedException thrown= ExpectedException.none();

  @Test
  public void throwsNothing() {
    // no exception expected, none thrown: passes.
  }

  @Test
  public void throwsNullPointerException() {
    thrown.expect(NullPointerException.class);
    throw new NullPointerException();
  }

  @Test
  public void throwsNullPointerExceptionWithMessage() {
    thrown.expect(NullPointerException.class);
    thrown.expectMessage("happened?");
    thrown.expectMessage(startsWith("What"));
    throw new NullPointerException("What happened?");
  }
}
Run Code Online (Sandbox Code Playgroud)

expectMessage()它可以是一个字符串(该消息的一个子)或匹配器,所以你可以做正则表达式检查或什么的.