软断言在后续测试失败时抛出异常

时间:2017-10-11 06:50:53

标签: testing assertj

根据标题,我试图在循环中运行测试用例。为了能够计算失败的断言的数量,我期望如果AssertJ试图从方法调用断言返回的值,它应该轻轻失败一次迭代并继续。否则,它无视软断言的目的。这是一个说明这一点的片段:

    public static void main(String[] args) {
        SoftAssertions softAssertions = new SoftAssertions();
        softAssertions.assertThat(throwException(10)).isTrue();
        softAssertions.assertThat(throwException(10)).isTrue();
        softAssertions.assertThat(throwException(1)).isTrue();
        softAssertions.assertAll();
    }

    private static boolean throwException(int stuff){
        if(stuff == 1){
           throw new RuntimeException();
       }
       return true;
    }

输出:

   Exception in thread "main" java.lang.RuntimeException
    at eLCMUpdate.throwException(MyClass.java:101)
    at eLCMUpdate.main(MyClass.java:95)

我在这里遗漏了一些东西。我做错了吗?

2 个答案:

答案 0 :(得分:1)

根据我的理解,软断言可以处理布尔值而不是异常。

另外:如果在调用softAssertions.assertAll()之前抛出异常,显然这个方法也永远不会被执行。这实际上是您报告的行为的原因。

只需尝试调试代码,您就会看到永远不会调用softAssertions.assertAll()

如果您将代码更改为:

,软断言将正常工作
@Test
void soft_assertions() {
    SoftAssertions softAssertions = new SoftAssertions();
    softAssertions.assertThat(checkCondition(10)).isTrue();
    softAssertions.assertThat(checkCondition(10)).isTrue();
    softAssertions.assertThat(checkCondition(1)).isTrue();
    softAssertions.assertThat(checkCondition(2)).isTrue();
    softAssertions.assertThat(checkCondition(20)).isTrue();
    softAssertions.assertAll();
}

private static boolean checkCondition(int stuff){
    if(stuff == 1 || stuff == 2){
        return false;
    }
    return true;
}

这将输出多个断言的结果,而不是在第一个失败的断言的评估上停止。

输出:

org.assertj.core.api.SoftAssertionError: 
The following 2 assertions failed:
1) 
Expecting:
 <false>
to be equal to:
 <true>
but was not.
at JsonStewardshipCustomerConversionTest.soft_assertions(JsonStewardshipCustomerConversionTest.java:301)
2) 
Expecting:
 <false>
to be equal to:
 <true>
but was not.
at JsonStewardshipCustomerConversionTest.soft_assertions(JsonStewardshipCustomerConversionTest.java:302)

更新

SoftAssertion似乎不适合您的目的。

我建议您使用JUnit 5 assertAll。根据我的测试,它评估assertAll块中的所有条件,并且也存在异常。这里的问题是你需要JUnit 5,它可能还没有被大量采用。

这是一个布尔条件失败的例子,也是一个例外。两者都在控制台中报告。

@Test
void soft_assertions() {
    assertAll("Check condition",
            () -> assertThat(checkCondition(9)).isTrue(),
            () -> assertThat(checkCondition(10)).isTrue(),
            () -> assertThat(checkCondition(11)).isTrue(),
            () -> assertThat(checkCondition(2)).isTrue(), // Throws exception
            () -> assertThat(checkCondition(3)).isFalse(), // fails
            () -> assertThrows(IllegalArgumentException.class, () -> {
                checkCondition(1);
            })
    );
}

private static boolean checkCondition(int stuff) {
    if (stuff == 1 || stuff == 2) {
        throw new IllegalArgumentException();
    }
    return true;
}

您将在输出中看到:

org.opentest4j.MultipleFailuresError: Check condition (2 failures)
    <no message> in java.lang.IllegalArgumentException

Expecting:
 <true>
to be equal to:
 <false>
but was not.

答案 1 :(得分:1)

代码softAssertions.assertThat(throwException(10)).isTrue();中的问题是,如果抛出异常,则根本不会执行assertThat

您需要的是懒惰评估您在assertThat传递的代码,您可以使用AssertJ assertThatCode执行此操作,如下所示:

final SoftAssertions softAssertions = new SoftAssertions();
softAssertions.assertThatCode(() -> throwException(10)).doesNotThrowAnyException();
softAssertions.assertThatCode(() -> throwException(1)).isInstanceOf(RuntimeException.class);
softAssertions.assertAll();