Can I 'soft assert' json with WebTestClient?

37 Views Asked by At

I have a endpoint returning some json looking like that :

{
    "subCategories": [
        {
            "code": "1",
            "libelle": "foo"
        },
        {
            "code": "2",
            "libelle": "bar"
        }
    ]
}

I also have a test :

@SpringBootTest
class MyJsonTest {

    private WebTestClient webClient;

    @BeforeEach
    public void before() {
        webClient = WebTestClient
                .bindToServer()
                .baseUrl("http://some-server/")
                .build();
    }

    @Test
    public void testAssertJson() {
        webClient.get().uri(builder -> builder.path("/some-endpoint").build())
        .exchange()        
        .expectBody()
            .jsonPath("$.subCategories[0].code").isEqualTo("1")
            .jsonPath("$.subCategories[0].libelle").isEqualTo("foo");
    }
}

This works fine.

However, I would like to 'assert softly' my json assertions, to report several errors in one go. I expected this to work :

    @Test
    public void testAssertJson() {
        webClient.get().uri(builder -> builder.path("/some-endpoint").build())
        .exchange()
        .expectAll(
                r -> r.expectBody().jsonPath("$.subCategories[0].code").isEqualTo("1"),
                r -> r.expectBody().jsonPath("$.subCategories[0].libelle").isEqualTo("foo"));
    }

However the second assertion fails with the following :

java.lang.AssertionError: No value at JSON path "$.subCategories[0].libelle"
    at org.springframework.test.util.JsonPathExpectationsHelper.evaluateJsonPath(JsonPathExpectationsHelper.java:302)
    at org.springframework.test.util.JsonPathExpectationsHelper.assertValue(JsonPathExpectationsHelper.java:99)
    at org.springframework.test.web.reactive.server.JsonPathAssertions.isEqualTo(JsonPathAssertions.java:54)
    at fr.mutex.digital.oscar.collectifapi.integrationtests.IntegrationTestsApplicationTests.lambda$5(IntegrationTestsApplicationTests.java:71)
    at org.springframework.test.web.reactive.server.DefaultWebTestClient$DefaultResponseSpec.lambda$expectAll$1(DefaultWebTestClient.java:510)
    at org.springframework.test.util.ExceptionCollector.execute(ExceptionCollector.java:49)
    at org.springframework.test.web.reactive.server.DefaultWebTestClient$DefaultResponseSpec.expectAll(DefaultWebTestClient.java:510)
    at fr.mutex.digital.oscar.collectifapi.integrationtests.IntegrationTestsApplicationTests.testAssertJson(IntegrationTestsApplicationTests.java:69)
    at java.base/java.lang.reflect.Method.invoke(Method.java:568)
    at java.base/java.util.ArrayList.forEach(ArrayList.java:1511)
    at java.base/java.util.ArrayList.forEach(ArrayList.java:1511)
Caused by: java.lang.IllegalArgumentException: json can not be null or empty
    at com.jayway.jsonpath.internal.Utils.notEmpty(Utils.java:401)
    at com.jayway.jsonpath.JsonPath.read(JsonPath.java:390)
    at com.jayway.jsonpath.JsonPath.read(JsonPath.java:377)
    at org.springframework.test.util.JsonPathExpectationsHelper.evaluateJsonPath(JsonPathExpectationsHelper.java:299)
    ... 10 more

If I comment the 1st assertion, the 2nd passes again; so the json path seems ok.

I checked some webtestclient/json related questions on stackoverflow, but could not find an answer.

Am I misunderstanding the API ?

Spring boot version is 3.2.2 , with java 17.

Only dependencies are spring-boot-starter-webflux and spring-boot-starter-webflux

Regards

0

There are 0 best solutions below