[英]JUnit4 @Test(expected=MyException.class) VS try/catch
我正在考虑异常处理和单元测试最佳实践,因为我们正在努力获得一些代码最佳实践。
我们公司维基上发现的前一篇关于最佳实践的文章指出“不要使用try / catch,而是使用Junit4 @Test(expect = MyException.class)”,没有进一步的信息。 我不相信。
我们的许多自定义异常都有一个枚举,以便识别失败原因。 结果,我宁愿看到如下的测试:
@Test
public void testDoSomethingFailsBecauseZzz() {
try{
doSomething();
} catch(OurCustomException e){
assertEquals("Omg it failed, but not like we planned", FailureEnum.ZZZ, e.getFailure());
}
}
比:
@Test(expected = OurCustomException.class)
public void testDoSomethingFailsBecauseZzz() {
doSomething();
}
当doSomethig()看起来像:
public void doSomething throws OurCustomException {
if(Aaa) {
throw OurCustomException(FailureEnum.AAA);
}
if(Zzz) {
throw OurCustomException(FailureEnum.ZZZ);
}
// ...
}
在旁注中,我更确信在某些情况下@Test(expected = blabla.class)是最佳选择(例如,当异常是精确的并且毫无疑问导致它的原因时)。
我在这里遗漏了什么,还是应该在必要时推动使用try / catch?
听起来你的枚举被用作异常层次结构的替代品? 也许如果你有一个异常层次结构, @Test(expected=XYZ.class)
会变得更有用吗?
expected
属性。 在你的情况下,似乎你想要后者(断言异常有一定的FailureEnum
值); 使用try/catch
没有任何问题 。
你应该“不使用try / catch”(解释为“从不”)的概括是无聊的。
杰夫是对的; 您的异常层次结构的组织是可疑的。 但是,你似乎认识到这一点。 :)
如果要检查原始异常类型,则expected
方法是合适的。 否则,如果你需要测试关于异常的一些东西(并且无论测试消息内容的enum
怪异是否常见)你都可以尝试catch,但这有点老了。 新的JUnit方法是使用MethodRule
。 API中出现的一个( ExpectedException
)是专门测试消息,但是您可以轻松查看代码并调整该实现以检查失败enum
。
我在搜索如何处理异常时遇到了这个问题。
正如@Yishai所提到的,期望异常的首选方法是使用JUnit规则和ExpectedException
。
当使用@Test(expected=SomeException.class)
如果在方法中的任何位置抛出异常,则测试方法将通过。
使用ExpectedException
:
@Test
public void testException()
{
// If SomeException is thrown here, the test will fail.
expectedException.expect(SomeException.class);
// If SomeException is thrown here, the test will pass.
}
你也可以测试:
ExpectedException.expectMessage()
; expectedException.expectCause()
。 作为旁注:我不认为使用枚举来处理异常消息/原因是一种很好的做法。 (如果我错了,请纠正我。)
在您的特殊情况下,您希望测试(1)是否抛出预期的异常类型 ,以及(2)如果错误号是正确的,因为该方法可以使用不同的类型抛出相同的异常。
这需要检查异常对象。 但是,您可以坚持建议并验证是否抛出了正确的异常:
@Test(expected = OurCustomException.class)
public void testDoSomethingFailsBecauseZzz() {
try {
doSomething();
} catch (OurCustomException e) {
if (e.getFailureEnum.equals(FailureEnum.ZZZ)) // use *your* method here
throw e;
fail("Catched OurCostomException with unexpected failure number: "
+ e.getFailureEnum().getValue()); // again: your enum method here
}
}
此模式将
吃掉意外的异常并使测试失败。
编辑
改变它是因为我错过了显而易见的事情:我们可以使测试用例失败并捕获消息。 所以现在:如果抛出了带有预期错误代码的预期异常,则测试通过。 如果由于我们遇到意外错误而导致测试失败,那么我们就可以读取错误代码。
我做了一个例外,因为我遇到了和你一样的问题,Stph。 使用catch-exception,您的代码可能如下所示:
@Test
public void testDoSomethingFailsBecauseZzz() {
verifyException(myObj, OurCustomException.class).doSomething();
assertEquals("Omg it failed, but not like we planned", FailureEnum.ZZZ,
((OurCustomException)caughtException()).getFailure() ;
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.