spring-cloud / spring-cloud-contract

Support for Consumer Driven Contracts in Spring
https://cloud.spring.io/spring-cloud-contract
Apache License 2.0
720 stars 440 forks source link

Autogenerated tests aren't asserting empty objects. #554

Closed AlexanderPruss closed 6 years ago

AlexanderPruss commented 6 years ago

Version: Spring Cloud Contract 1.2.1

Similar to https://github.com/spring-cloud/spring-cloud-contract/issues/203, but for maps/objects instead of arrays.

I'm writing a contract for a service that whose responses sometime contain an empty object like this:

{
    "thisObjectIsHere" : "yep",
    "thisObjectIsEmpty" : {}
}

I haven't figured out any way to get the contract test to check for the presence of an empty thisObjectIsEmpty object. I can test for empty arrays, but not for empty objects.

Testing for empty arrays generates code testing for an empty array:

//contract
body([
     thisObjectsHere : "yep",
     thisObjectIsMissing: []
])
// generates:
...
assertThatJson(parsedJson).field("['thisObjectIsHere']").isEqualTo("yep");
assertThatJson(parsedJson).array("['thisObjectIsMissing']").isEmpty();
...

But testing for empty objects does't work, the empty object is completely omitted from generated code:

//contract
body([
     thisObjectsHere : "yep",
     thisObjectIsMissing: [:]
])
// generates:
...
assertThatJson(parsedJson).field("['thisObjectIsHere']").isEqualTo("yep");
//The missing object is completely absent from the generated test!
...
marcingrzejszczak commented 6 years ago

I guess this will require work on the https://github.com/marcingrzejszczak/jsonassert side to add the isEmpty() (or sth like this) method, I'll have to double check how the json path on the WireMock side would look like.

As a workaround, you can use the stubMatcher / testMatcher section to provide the jsonpath manually.

marcingrzejszczak commented 6 years ago

Actually this issue is completely focusing on the response side. I'll try to take a look at a situation where an empty map is returned in order to assert if it's empty.