概述
有一段时间,人们会希望并期望JUnit @Test案例失败。 尽管这种情况很少见,但确实发生了。 我需要检测JUnit测试何时失败,然后(如果期望的话)通过而不是失败。 具体情况是我正在测试一段代码,该代码可能会在对象调用内引发Assert错误。 该代码被编写为对流行的新Fest Assertions框架的增强,因此,为了测试功能,人们可能希望测试用例会故意失败。
一个解法
一种可能的解决方案是将JUnit @Rule提供的功能与注释形式的自定义标记一起使用。
为什么要使用@Rule?
@Rule对象为测试类和每个测试用例提供了类似于AOP的接口。 在运行每个测试用例之前,将重置规则,并且它们以@Around AspectJ建议的样式公开测试用例的工作方式。
必需的代码元素
- @Rule对象检查每个@Test用例的状态
- @ExpectedFailure自定义标记注释
- 测试用例证明代码有效!
- 如果带注释的测试用例没有失败,则抛出可选的特定异常
注意:工作代码在我的github页面上可用,并已添加到Maven Central。 随意分叉项目并提交拉取请求 Maven用法
<dependency>
<groupId>com.clickconcepts.junit</groupId>
<artifactId>expected-failure</artifactId>
<version>0.0.9</version>
</dependency>
用法示例
在此示例中,“ exception”对象是Fest断言增强的ExpectedException(请查看我的下一篇文章以展示此功能)。 预期的异常将产生断言,并且为了测试这些断言,必须将测试用例标记为@ExpectedFailure
public class ExceptionAssertTest {
@Rule
public ExpectedException exception = ExpectedException.none();
@Rule
public ExpectedTestFailureWatcher watcher = ExpectedTestFailureWatcher.instance();
@Test
@ExpectedFailure('The matcher should fail becasue exception is not a SimpleException')
public void assertSimpleExceptionAssert_exceptionIsOfType() {
// expected exception will be of type 'SimpleException'
exception.instanceOf(SimpleException.class);
// throw something other than SimpleException...expect failure
throw new RuntimeException('this is an exception');
}
}
解决方案的实施
提醒一下,最新代码可在我的github页面上找到 。
@规则代码(ExpectedTestFailureWatcher.java)
import org.junit.rules.TestRule;
import org.junit.runner.Description;
import org.junit.runners.model.Statement;
// YEAH Guava!!
import static com.google.common.base.Strings.isNullOrEmpty;
public class ExpectedTestFailureWatcher implements TestRule {
/**
* Static factory to an instance of this watcher
*
* @return New instance of this watcher
*/
public static ExpectedTestFailureWatcher instance() {
return new ExpectedTestFailureWatcher();
}
@Override
public Statement apply(final Statement base, final Description description) {
return new Statement() {
@Override
public void evaluate() throws Throwable {
boolean expectedToFail = description.getAnnotation(ExpectedFailure.class) != null;
boolean failed = false;
try {
// allow test case to execute
base.evaluate();
} catch (Throwable exception) {
failed = true;
if (!expectedToFail) {
throw exception; // did not expect to fail and failed...fail
}
}
// placed outside of catch
if (expectedToFail && !failed) {
throw new ExpectedTestFailureException(getUnFulfilledFailedMessage(description));
}
}
/**
* Extracts detailed message about why test failed
* @param description
* @return
*/
private String getUnFulfilledFailedMessage(Description description) {
String reason = null;
if (description.getAnnotation(ExpectedFailure.class) != null) {
reason = description.getAnnotation(ExpectedFailure.class).reason();
}
if (isNullOrEmpty(reason)) {
reason = 'Should have failed but didn't';
}
return reason;
}
};
}
}
@ExpectedFailure定制注释(ExpectedFailure.java)
import java.lang.annotation.*;
/**
* Initially this is just a marker annotation to be used by a JUnit4 Test case in conjunction
* with ExpectedTestFailure @Rule to indicate that a test is supposed to be failing
*/
@Documented
@Retention(RetentionPolicy.RUNTIME)
@Target(value = ElementType.METHOD)
public @interface ExpectedFailure {
// TODO: enhance by adding specific information about what type of failure expected
//Class
assertType() default Throwable.class;
/**
* Text based reason for marking test as ExpectedFailure
* @return String
*/
String reason() default '';
}
自定义异常(可选,您可以轻松地抛出RuntimeException或现有的自定义异常)
public class ExpectedTestFailureException extends Throwable {
public ExpectedTestFailureException(String message) {
super(message);
}
}
一个人不能利用预期的故障标记能力吗?
强大的功能伴随着巨大的责任 ,建议您如果不完全了解测试失败的原因,请不要将测试标记为@ExpectedFailure。 建议谨慎执行此测试方法。 请勿使用@ExpectedFailure注释替代@Ignore
将来可能的增强可能包括指定在测试用例执行期间确定的特定断言或特定消息的方法。
已知的问题
在此当前状态下,@ ExpectedFailure批注可以掩盖其他声明,并且在将来进行增强之前,建议明智地使用此方法。
参考:在Mike的站点博客上,允许JUnit测试通过我们的JCG合作伙伴 Mike的失败测试案例 。
翻译自: https://www.javacodegeeks.com/2012/09/junit-pass-test-case-on-failures.html
最后
以上就是寒冷小霸王为你收集整理的JUnit通过失败测试案例的全部内容,希望文章能够帮你解决JUnit通过失败测试案例所遇到的程序开发问题。
如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。
发表评论 取消回复