From 7341b570b8f5b0d054d6d91e29b3a1fe122323aa Mon Sep 17 00:00:00 2001 From: Marcin Grzejszczak Date: Tue, 8 May 2018 20:38:00 +0200 Subject: [PATCH 1/3] Added better support for XML in RestDocs; fixes gh-647 --- .../contracts/com/example/server/pom.xml | 2 +- samples/standalone/dsl/http-client/pom.xml | 2 +- samples/standalone/dsl/http-server/pom.xml | 2 +- .../standalone/messaging/stream-sink/pom.xml | 2 +- .../messaging/stream-source/pom.xml | 2 +- .../standalone/pact/pact-http-client/pom.xml | 2 +- .../standalone/pact/pact-http-server/pom.xml | 2 +- .../restdocs/http-client/build.gradle | 3 +- .../standalone/restdocs/http-client/pom.xml | 6 +- .../com/example/loan/XmlServiceTests.java | 84 +++++++++++++++++++ .../loan/XmlServiceUsingStubRunnerTests.java | 57 +++++++++++++ .../restdocs/http-server/build.gradle | 1 + .../standalone/restdocs/http-server/pom.xml | 6 +- .../fraud/FraudDetectionXmlController.java | 47 +++++++++++ .../example/fraud/XmlStubGeneratorTests.java | 60 +++++++++++++ samples/standalone/yml/http-client/pom.xml | 2 +- samples/standalone/yml/http-server/pom.xml | 2 +- .../projects/complex-configuration/pom.xml | 2 +- .../module/pom.xml | 2 +- .../test/projects/plugin-extension/pom.xml | 2 +- .../test/projects/spring-boot-groovy/pom.xml | 2 +- .../test/projects/spring-boot-java/pom.xml | 2 +- .../wiremock/restdocs/WireMockSnippet.java | 16 +++- .../restdocs/WireMockSnippetTests.java | 64 +++++++++++++- 24 files changed, 353 insertions(+), 19 deletions(-) create mode 100644 samples/standalone/restdocs/http-client/src/test/java/com/example/loan/XmlServiceTests.java create mode 100644 samples/standalone/restdocs/http-client/src/test/java/com/example/loan/XmlServiceUsingStubRunnerTests.java create mode 100644 samples/standalone/restdocs/http-server/src/main/java/com/example/fraud/FraudDetectionXmlController.java create mode 100644 samples/standalone/restdocs/http-server/src/test/java/com/example/fraud/XmlStubGeneratorTests.java diff --git a/samples/standalone/contracts/com/example/server/pom.xml b/samples/standalone/contracts/com/example/server/pom.xml index 729a9f012c..6b4522c76b 100644 --- a/samples/standalone/contracts/com/example/server/pom.xml +++ b/samples/standalone/contracts/com/example/server/pom.xml @@ -13,7 +13,7 @@ org.springframework.boot spring-boot-starter-parent - 1.5.10.RELEASE + 1.5.12.RELEASE diff --git a/samples/standalone/dsl/http-client/pom.xml b/samples/standalone/dsl/http-client/pom.xml index 4977156548..75c4228df4 100644 --- a/samples/standalone/dsl/http-client/pom.xml +++ b/samples/standalone/dsl/http-client/pom.xml @@ -13,7 +13,7 @@ org.springframework.boot spring-boot-starter-parent - 1.5.10.RELEASE + 1.5.12.RELEASE diff --git a/samples/standalone/dsl/http-server/pom.xml b/samples/standalone/dsl/http-server/pom.xml index 1005cb161d..9a5369ace0 100644 --- a/samples/standalone/dsl/http-server/pom.xml +++ b/samples/standalone/dsl/http-server/pom.xml @@ -13,7 +13,7 @@ org.springframework.boot spring-boot-starter-parent - 1.5.10.RELEASE + 1.5.12.RELEASE diff --git a/samples/standalone/messaging/stream-sink/pom.xml b/samples/standalone/messaging/stream-sink/pom.xml index 4ab6a0fff0..a942e9e886 100644 --- a/samples/standalone/messaging/stream-sink/pom.xml +++ b/samples/standalone/messaging/stream-sink/pom.xml @@ -14,7 +14,7 @@ org.springframework.boot spring-boot-starter-parent - 1.5.10.RELEASE + 1.5.12.RELEASE diff --git a/samples/standalone/messaging/stream-source/pom.xml b/samples/standalone/messaging/stream-source/pom.xml index 830622d815..be6a0cc184 100644 --- a/samples/standalone/messaging/stream-source/pom.xml +++ b/samples/standalone/messaging/stream-source/pom.xml @@ -14,7 +14,7 @@ org.springframework.boot spring-boot-starter-parent - 1.5.10.RELEASE + 1.5.12.RELEASE diff --git a/samples/standalone/pact/pact-http-client/pom.xml b/samples/standalone/pact/pact-http-client/pom.xml index fc119c939f..d014662e15 100644 --- a/samples/standalone/pact/pact-http-client/pom.xml +++ b/samples/standalone/pact/pact-http-client/pom.xml @@ -13,7 +13,7 @@ org.springframework.boot spring-boot-starter-parent - 1.5.10.RELEASE + 1.5.12.RELEASE diff --git a/samples/standalone/pact/pact-http-server/pom.xml b/samples/standalone/pact/pact-http-server/pom.xml index aedbe37ede..198571c7ae 100644 --- a/samples/standalone/pact/pact-http-server/pom.xml +++ b/samples/standalone/pact/pact-http-server/pom.xml @@ -13,7 +13,7 @@ org.springframework.boot spring-boot-starter-parent - 1.5.10.RELEASE + 1.5.12.RELEASE diff --git a/samples/standalone/restdocs/http-client/build.gradle b/samples/standalone/restdocs/http-client/build.gradle index 3457d39d16..1b0ef336e6 100644 --- a/samples/standalone/restdocs/http-client/build.gradle +++ b/samples/standalone/restdocs/http-client/build.gradle @@ -36,7 +36,8 @@ dependencyManagement { dependencies { compile("org.springframework.boot:spring-boot-starter-web") compile("org.springframework.boot:spring-boot-starter-actuator") - + compile("com.fasterxml.jackson.dataformat:jackson-dataformat-xml") + testCompile 'org.springframework.cloud:spring-cloud-contract-wiremock' testCompile 'org.springframework.cloud:spring-cloud-starter-contract-stub-runner' testCompile "org.springframework.boot:spring-boot-starter-test" diff --git a/samples/standalone/restdocs/http-client/pom.xml b/samples/standalone/restdocs/http-client/pom.xml index a46e29d780..6a7abc768a 100644 --- a/samples/standalone/restdocs/http-client/pom.xml +++ b/samples/standalone/restdocs/http-client/pom.xml @@ -13,7 +13,7 @@ org.springframework.boot spring-boot-starter-parent - 1.5.10.RELEASE + 1.5.12.RELEASE @@ -32,6 +32,10 @@ org.springframework.boot spring-boot-starter-actuator + + com.fasterxml.jackson.dataformat + jackson-dataformat-xml + diff --git a/samples/standalone/restdocs/http-client/src/test/java/com/example/loan/XmlServiceTests.java b/samples/standalone/restdocs/http-client/src/test/java/com/example/loan/XmlServiceTests.java new file mode 100644 index 0000000000..351ce62021 --- /dev/null +++ b/samples/standalone/restdocs/http-client/src/test/java/com/example/loan/XmlServiceTests.java @@ -0,0 +1,84 @@ +package com.example.loan; + +import java.net.URI; +import java.nio.charset.Charset; + +import com.github.tomakehurst.wiremock.WireMockServer; +import com.github.tomakehurst.wiremock.stubbing.StubMapping; +import org.assertj.core.api.BDDAssertions; +import org.junit.Test; +import org.junit.runner.RunWith; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.beans.factory.annotation.Value; +import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.cloud.contract.wiremock.AutoConfigureWireMock; +import org.springframework.core.io.Resource; +import org.springframework.http.MediaType; +import org.springframework.http.RequestEntity; +import org.springframework.http.ResponseEntity; +import org.springframework.test.context.junit4.SpringRunner; +import org.springframework.util.StreamUtils; +import org.springframework.web.client.RestTemplate; + +@RunWith(SpringRunner.class) +@SpringBootTest(properties="service.port=${wiremock.server.port}") +@AutoConfigureWireMock(port=0) +public class XmlServiceTests { + + @Value("classpath:META-INF/com.example/http-server-restdocs/0.0.1-SNAPSHOT/mappings/should_return_empty_content.json") + private Resource empty; + + @Value("classpath:META-INF/com.example/http-server-restdocs/0.0.1-SNAPSHOT/mappings/should_return_full_content.json") + private Resource full; + + @Autowired + private WireMockServer server; + + @Test + public void shouldSuccessfullyReturnFullResponse() throws Exception { + server.addStubMapping(StubMapping.buildFrom(StreamUtils.copyToString( + full.getInputStream(), Charset.forName("UTF-8")))); + + ResponseEntity responseEntity = new RestTemplate().exchange( + RequestEntity.post(URI.create("http://localhost:" + server.port() + "/xmlfraud")) + .contentType(MediaType.valueOf("application/xml;charset=UTF-8")) + .body(new XmlRequestBody("foo")), XmlResponseBody.class); + + BDDAssertions.then(responseEntity.getStatusCodeValue()).isEqualTo(200); + BDDAssertions.then(responseEntity.getBody().status).isEqualTo("FULL"); + } + + @Test + public void shouldSuccessfullyReturnEmptyResponse() throws Exception { + server.addStubMapping(StubMapping.buildFrom(StreamUtils.copyToString( + empty.getInputStream(), Charset.forName("UTF-8")))); + + ResponseEntity responseEntity = new RestTemplate().exchange( + RequestEntity.post(URI.create("http://localhost:" + server.port() + "/xmlfraud")) + .contentType(MediaType.valueOf("application/xml;charset=UTF-8")) + .body(new XmlRequestBody("")), XmlResponseBody.class); + + BDDAssertions.then(responseEntity.getStatusCodeValue()).isEqualTo(200); + BDDAssertions.then(responseEntity.getBody().status).isEqualTo("EMPTY"); + } + +} + +class XmlRequestBody { + public String name; + + public XmlRequestBody(String name) { + this.name = name; + } +} + +class XmlResponseBody { + public String status; + + public XmlResponseBody(String status) { + this.status = status; + } + + public XmlResponseBody() { + } +} \ No newline at end of file diff --git a/samples/standalone/restdocs/http-client/src/test/java/com/example/loan/XmlServiceUsingStubRunnerTests.java b/samples/standalone/restdocs/http-client/src/test/java/com/example/loan/XmlServiceUsingStubRunnerTests.java new file mode 100644 index 0000000000..bd7b47e2a6 --- /dev/null +++ b/samples/standalone/restdocs/http-client/src/test/java/com/example/loan/XmlServiceUsingStubRunnerTests.java @@ -0,0 +1,57 @@ +package com.example.loan; + +import java.net.URI; +import java.nio.charset.Charset; + +import com.example.loan.model.Client; +import com.example.loan.model.LoanApplication; +import com.example.loan.model.LoanApplicationResult; +import com.example.loan.model.LoanApplicationStatus; +import com.github.tomakehurst.wiremock.stubbing.StubMapping; +import org.assertj.core.api.BDDAssertions; +import org.junit.Before; +import org.junit.Test; +import org.junit.runner.RunWith; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.beans.factory.annotation.Value; +import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.cloud.contract.stubrunner.spring.AutoConfigureStubRunner; +import org.springframework.http.MediaType; +import org.springframework.http.RequestEntity; +import org.springframework.http.ResponseEntity; +import org.springframework.test.context.junit4.SpringRunner; +import org.springframework.util.StreamUtils; +import org.springframework.web.client.RestTemplate; + +import static org.assertj.core.api.Assertions.assertThat; + +@RunWith(SpringRunner.class) +@SpringBootTest +@AutoConfigureStubRunner(ids = "com.example:http-server-restdocs") +public class XmlServiceUsingStubRunnerTests { + + @Value("${stubrunner.runningstubs.http-server-restdocs.port}") int port; + + @Test + public void shouldSuccessfullyReturnFullResponse() throws Exception { + ResponseEntity responseEntity = new RestTemplate().exchange( + RequestEntity.post(URI.create("http://localhost:" + this.port + "/xmlfraud")) + .contentType(MediaType.valueOf("application/xml;charset=UTF-8")) + .body(new XmlRequestBody("foo")), XmlResponseBody.class); + + BDDAssertions.then(responseEntity.getStatusCodeValue()).isEqualTo(200); + BDDAssertions.then(responseEntity.getBody().status).isEqualTo("FULL"); + } + + @Test + public void shouldSuccessfullyReturnEmptyResponse() throws Exception { + ResponseEntity responseEntity = new RestTemplate().exchange( + RequestEntity.post(URI.create("http://localhost:" + this.port + "/xmlfraud")) + .contentType(MediaType.valueOf("application/xml;charset=UTF-8")) + .body(new XmlRequestBody("")), XmlResponseBody.class); + + BDDAssertions.then(responseEntity.getStatusCodeValue()).isEqualTo(200); + BDDAssertions.then(responseEntity.getBody().status).isEqualTo("EMPTY"); + } + +} diff --git a/samples/standalone/restdocs/http-server/build.gradle b/samples/standalone/restdocs/http-server/build.gradle index d1fc271858..35fba99dc6 100644 --- a/samples/standalone/restdocs/http-server/build.gradle +++ b/samples/standalone/restdocs/http-server/build.gradle @@ -40,6 +40,7 @@ dependencyManagement { dependencies { compile("org.springframework.boot:spring-boot-starter-web") compile("org.springframework.boot:spring-boot-starter-actuator") + compile("com.fasterxml.jackson.dataformat:jackson-dataformat-xml") testCompile 'org.springframework.boot:spring-boot-starter-test' testCompile 'org.springframework.restdocs:spring-restdocs-mockmvc' diff --git a/samples/standalone/restdocs/http-server/pom.xml b/samples/standalone/restdocs/http-server/pom.xml index bd310fbd38..d1c326b0f3 100644 --- a/samples/standalone/restdocs/http-server/pom.xml +++ b/samples/standalone/restdocs/http-server/pom.xml @@ -13,7 +13,7 @@ org.springframework.boot spring-boot-starter-parent - 1.5.10.RELEASE + 1.5.12.RELEASE @@ -32,6 +32,10 @@ org.springframework.boot spring-boot-starter-actuator + + com.fasterxml.jackson.dataformat + jackson-dataformat-xml + org.springframework.boot diff --git a/samples/standalone/restdocs/http-server/src/main/java/com/example/fraud/FraudDetectionXmlController.java b/samples/standalone/restdocs/http-server/src/main/java/com/example/fraud/FraudDetectionXmlController.java new file mode 100644 index 0000000000..afc1cd1073 --- /dev/null +++ b/samples/standalone/restdocs/http-server/src/main/java/com/example/fraud/FraudDetectionXmlController.java @@ -0,0 +1,47 @@ +package com.example.fraud; + +import java.math.BigDecimal; + +import com.example.fraud.model.FraudCheck; +import org.springframework.http.MediaType; +import org.springframework.stereotype.Controller; +import org.springframework.util.StringUtils; +import org.springframework.web.bind.annotation.RequestBody; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.ResponseBody; + +import static org.springframework.web.bind.annotation.RequestMethod.POST; +import static org.springframework.web.bind.annotation.RequestMethod.PUT; + +@Controller +public class FraudDetectionXmlController { + + @RequestMapping( + value = "/xmlfraud", + method = POST, + consumes = MediaType.APPLICATION_XML_VALUE, + produces = MediaType.APPLICATION_XML_VALUE) + @ResponseBody + public XmlResponseBody xmlResponseBody(@RequestBody XmlRequestBody xmlRequestBody) { + if (StringUtils.isEmpty(xmlRequestBody.name)) { + return new XmlResponseBody("EMPTY"); + } + return new XmlResponseBody("FULL"); + } + +} + +class XmlRequestBody { + public String name; +} + +class XmlResponseBody { + public String status; + + public XmlResponseBody(String status) { + this.status = status; + } + + public XmlResponseBody() { + } +} \ No newline at end of file diff --git a/samples/standalone/restdocs/http-server/src/test/java/com/example/fraud/XmlStubGeneratorTests.java b/samples/standalone/restdocs/http-server/src/test/java/com/example/fraud/XmlStubGeneratorTests.java new file mode 100644 index 0000000000..b36e22bad5 --- /dev/null +++ b/samples/standalone/restdocs/http-server/src/test/java/com/example/fraud/XmlStubGeneratorTests.java @@ -0,0 +1,60 @@ +package com.example.fraud; + +import java.math.BigDecimal; + +import com.example.fraud.model.FraudCheck; +import com.fasterxml.jackson.databind.ObjectMapper; +import org.junit.Before; +import org.junit.Test; +import org.junit.runner.RunWith; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.boot.test.autoconfigure.json.AutoConfigureJsonTesters; +import org.springframework.boot.test.autoconfigure.restdocs.AutoConfigureRestDocs; +import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc; +import org.springframework.boot.test.context.SpringBootTest; +import org.springframework.boot.test.json.JacksonTester; +import org.springframework.http.MediaType; +import org.springframework.restdocs.mockmvc.MockMvcRestDocumentation; +import org.springframework.test.annotation.DirtiesContext; +import org.springframework.test.context.junit4.SpringRunner; +import org.springframework.test.web.servlet.MockMvc; +import org.springframework.test.web.servlet.request.MockMvcRequestBuilders; +import org.springframework.test.web.servlet.result.MockMvcResultMatchers; + +import static org.springframework.cloud.contract.wiremock.restdocs.WireMockRestDocs.verify; +import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.post; +import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.content; +import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.jsonPath; +import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status; + +@RunWith(SpringRunner.class) +@SpringBootTest(classes = Application.class) +@AutoConfigureRestDocs(outputDir = "target/snippets") +@AutoConfigureMockMvc +@DirtiesContext +public class XmlStubGeneratorTests { + + @Autowired + private MockMvc mockMvc; + + @Test + public void should_return_full_content() throws Exception { + mockMvc.perform(post("/xmlfraud") + .contentType(MediaType.APPLICATION_XML) + .content("foo")) + .andExpect(status().is2xxSuccessful()) + .andExpect(content().string("FULL")) + .andDo(MockMvcRestDocumentation.document("{methodName}")); + } + + @Test + public void should_return_empty_content() throws Exception { + mockMvc.perform(post("/xmlfraud") + .contentType(MediaType.APPLICATION_XML) + .content("")) + .andExpect(status().is2xxSuccessful()) + .andExpect(content().string("EMPTY")) + .andDo(MockMvcRestDocumentation.document("{methodName}")); + } + +} \ No newline at end of file diff --git a/samples/standalone/yml/http-client/pom.xml b/samples/standalone/yml/http-client/pom.xml index e5add8ab72..28f3b050e2 100644 --- a/samples/standalone/yml/http-client/pom.xml +++ b/samples/standalone/yml/http-client/pom.xml @@ -13,7 +13,7 @@ org.springframework.boot spring-boot-starter-parent - 1.5.10.RELEASE + 1.5.12.RELEASE diff --git a/samples/standalone/yml/http-server/pom.xml b/samples/standalone/yml/http-server/pom.xml index ffed0bfd43..41f261b8e5 100644 --- a/samples/standalone/yml/http-server/pom.xml +++ b/samples/standalone/yml/http-server/pom.xml @@ -13,7 +13,7 @@ org.springframework.boot spring-boot-starter-parent - 1.5.10.RELEASE + 1.5.12.RELEASE diff --git a/spring-cloud-contract-tools/spring-cloud-contract-maven-plugin/src/test/projects/complex-configuration/pom.xml b/spring-cloud-contract-tools/spring-cloud-contract-maven-plugin/src/test/projects/complex-configuration/pom.xml index 611f619493..a9c0d09566 100644 --- a/spring-cloud-contract-tools/spring-cloud-contract-maven-plugin/src/test/projects/complex-configuration/pom.xml +++ b/spring-cloud-contract-tools/spring-cloud-contract-maven-plugin/src/test/projects/complex-configuration/pom.xml @@ -28,7 +28,7 @@ org.springframework.boot spring-boot-starter-parent - 1.5.10.RELEASE + 1.5.12.RELEASE diff --git a/spring-cloud-contract-tools/spring-cloud-contract-maven-plugin/src/test/projects/different-module-configuration/module/pom.xml b/spring-cloud-contract-tools/spring-cloud-contract-maven-plugin/src/test/projects/different-module-configuration/module/pom.xml index 7b5cfdf966..cb72351664 100644 --- a/spring-cloud-contract-tools/spring-cloud-contract-maven-plugin/src/test/projects/different-module-configuration/module/pom.xml +++ b/spring-cloud-contract-tools/spring-cloud-contract-maven-plugin/src/test/projects/different-module-configuration/module/pom.xml @@ -28,7 +28,7 @@ org.springframework.boot spring-boot-starter-parent - 1.5.10.RELEASE + 1.5.12.RELEASE diff --git a/spring-cloud-contract-tools/spring-cloud-contract-maven-plugin/src/test/projects/plugin-extension/pom.xml b/spring-cloud-contract-tools/spring-cloud-contract-maven-plugin/src/test/projects/plugin-extension/pom.xml index 8aff9b4c45..ecaf5e79be 100644 --- a/spring-cloud-contract-tools/spring-cloud-contract-maven-plugin/src/test/projects/plugin-extension/pom.xml +++ b/spring-cloud-contract-tools/spring-cloud-contract-maven-plugin/src/test/projects/plugin-extension/pom.xml @@ -28,7 +28,7 @@ org.springframework.boot spring-boot-starter-parent - 1.5.10.RELEASE + 1.5.12.RELEASE diff --git a/spring-cloud-contract-tools/spring-cloud-contract-maven-plugin/src/test/projects/spring-boot-groovy/pom.xml b/spring-cloud-contract-tools/spring-cloud-contract-maven-plugin/src/test/projects/spring-boot-groovy/pom.xml index 82472d56a3..ae8ceaf4f5 100644 --- a/spring-cloud-contract-tools/spring-cloud-contract-maven-plugin/src/test/projects/spring-boot-groovy/pom.xml +++ b/spring-cloud-contract-tools/spring-cloud-contract-maven-plugin/src/test/projects/spring-boot-groovy/pom.xml @@ -28,7 +28,7 @@ org.springframework.boot spring-boot-starter-parent - 1.5.10.RELEASE + 1.5.12.RELEASE diff --git a/spring-cloud-contract-tools/spring-cloud-contract-maven-plugin/src/test/projects/spring-boot-java/pom.xml b/spring-cloud-contract-tools/spring-cloud-contract-maven-plugin/src/test/projects/spring-boot-java/pom.xml index 8aff9b4c45..ecaf5e79be 100644 --- a/spring-cloud-contract-tools/spring-cloud-contract-maven-plugin/src/test/projects/spring-boot-java/pom.xml +++ b/spring-cloud-contract-tools/spring-cloud-contract-maven-plugin/src/test/projects/spring-boot-java/pom.xml @@ -28,7 +28,7 @@ org.springframework.boot spring-boot-starter-parent - 1.5.10.RELEASE + 1.5.12.RELEASE diff --git a/spring-cloud-contract-wiremock/src/main/java/org/springframework/cloud/contract/wiremock/restdocs/WireMockSnippet.java b/spring-cloud-contract-wiremock/src/main/java/org/springframework/cloud/contract/wiremock/restdocs/WireMockSnippet.java index cec2f7ab04..84495e9f1c 100644 --- a/spring-cloud-contract-wiremock/src/main/java/org/springframework/cloud/contract/wiremock/restdocs/WireMockSnippet.java +++ b/spring-cloud-contract-wiremock/src/main/java/org/springframework/cloud/contract/wiremock/restdocs/WireMockSnippet.java @@ -46,6 +46,7 @@ import static com.github.tomakehurst.wiremock.client.WireMock.aResponse; import static com.github.tomakehurst.wiremock.client.WireMock.delete; import static com.github.tomakehurst.wiremock.client.WireMock.equalTo; import static com.github.tomakehurst.wiremock.client.WireMock.equalToJson; +import static com.github.tomakehurst.wiremock.client.WireMock.equalToXml; import static com.github.tomakehurst.wiremock.client.WireMock.get; import static com.github.tomakehurst.wiremock.client.WireMock.head; import static com.github.tomakehurst.wiremock.client.WireMock.matching; @@ -71,6 +72,7 @@ public class WireMockSnippet implements Snippet { private StubMapping stubMapping; private boolean hasJsonBodyRequestToMatch = false; + private boolean hasXmlBodyRequestToMatch = false; private final PropertyPlaceholderHelper propertyPlaceholderHelper = new PropertyPlaceholderHelper( "{", "}"); @@ -121,13 +123,22 @@ public class WireMockSnippet implements Snippet { .get("contract.contentType"); if (this.contentType == null) { this.hasJsonBodyRequestToMatch = hasJsonContentType(operation); + this.hasXmlBodyRequestToMatch = hasXmlContentType(operation); } } private boolean hasJsonContentType(Operation operation) { + return hasContentType(operation, MediaType.APPLICATION_JSON); + } + + private boolean hasXmlContentType(Operation operation) { + return hasContentType(operation, MediaType.APPLICATION_XML); + } + + private boolean hasContentType(Operation operation, MediaType mediaType) { return operation.getRequest().getHeaders().getContentType() != null && (operation.getRequest().getHeaders().getContentType() - .isCompatibleWith(MediaType.APPLICATION_JSON)); + .isCompatibleWith(mediaType)); } private ResponseDefinitionBuilder response(Operation operation) { @@ -196,6 +207,9 @@ public class WireMockSnippet implements Snippet { if (this.hasJsonBodyRequestToMatch) { builder.withRequestBody(equalToJson(content)); } + else if (this.hasXmlBodyRequestToMatch) { + builder.withRequestBody(equalToXml(content)); + } else { builder.withRequestBody(equalTo(content)); } diff --git a/spring-cloud-contract-wiremock/src/test/java/org/springframework/cloud/contract/wiremock/restdocs/WireMockSnippetTests.java b/spring-cloud-contract-wiremock/src/test/java/org/springframework/cloud/contract/wiremock/restdocs/WireMockSnippetTests.java index 7056e78279..60c6e0c57c 100644 --- a/spring-cloud-contract-wiremock/src/test/java/org/springframework/cloud/contract/wiremock/restdocs/WireMockSnippetTests.java +++ b/spring-cloud-contract-wiremock/src/test/java/org/springframework/cloud/contract/wiremock/restdocs/WireMockSnippetTests.java @@ -8,6 +8,7 @@ import java.nio.file.Files; import java.util.Collection; import com.github.tomakehurst.wiremock.matching.EqualToJsonPattern; +import com.github.tomakehurst.wiremock.matching.EqualToXmlPattern; import com.github.tomakehurst.wiremock.stubbing.StubMapping; import org.junit.Before; @@ -112,6 +113,25 @@ public class WireMockSnippetTests { .isEqualTo("{\"name\": \"12\"}"); } + @Test + public void should_use_equal_to_xml_pattern_for_body_when_request_content_type_is_xml_when_generating_stub() + throws Exception { + given(this.operation.getName()).willReturn("foo"); + WireMockSnippet snippet = new WireMockSnippet(); + given(this.operation.getRequest()).willReturn(requestPostWithXmlContentType()); + + snippet.document(this.operation); + + File stub = new File(this.outputFolder, "stubs/foo.json"); + assertThat(stub).exists(); + StubMapping stubMapping = WireMockStubMapping + .buildFrom(new String(Files.readAllBytes(stub.toPath()))); + assertThat(stubMapping.getRequest().getBodyPatterns().get(0)) + .isInstanceOf(EqualToXmlPattern.class); + assertThat(stubMapping.getRequest().getBodyPatterns().get(0).getValue()) + .isEqualTo("foo"); + } + @Test public void should_handle_empty_request_body() throws IOException { given(this.operation.getName()).willReturn("foo"); @@ -127,7 +147,6 @@ public class WireMockSnippetTests { assertThat(stubMapping.getRequest().getBodyPatterns()).isNullOrEmpty(); assertThat(stubMapping.getResponse().getStatus()) .isEqualTo(HttpStatus.ACCEPTED.value()); - } private OperationResponse response() { @@ -238,6 +257,49 @@ public class WireMockSnippetTests { }; } + private OperationRequest requestPostWithXmlContentType() { + return new OperationRequest() { + + @Override + public byte[] getContent() { + String content = "foo"; + return content.getBytes(Charset.forName("UTF-8")); + } + + @Override + public String getContentAsString() { + return "foo"; + } + + @Override + public HttpHeaders getHeaders() { + HttpHeaders httpHeaders = new HttpHeaders(); + httpHeaders.add("Content-Type", MediaType.APPLICATION_XML_VALUE); + return httpHeaders; + } + + @Override + public HttpMethod getMethod() { + return HttpMethod.POST; + } + + @Override + public Parameters getParameters() { + return null; + } + + @Override + public Collection getParts() { + return null; + } + + @Override + public URI getUri() { + return URI.create("http://foo/bar"); + } + }; + } + private OperationRequest requestPostWithEmptyBody() { return new OperationRequest() { @Override From bf1c54dec7a29f6983e4cccb6afaf8271fa4fc58 Mon Sep 17 00:00:00 2001 From: Tim Ysewyn Date: Fri, 11 May 2018 01:31:36 +0200 Subject: [PATCH 2/3] Added assertion for empty map/object to autogenerated test (#653) * Added assertion for empty map/object to autogenerated test Fixes #554 --- .../util/JsonToJsonPathsConverter.groovy | 8 ++- .../MockMvcMethodBodyBuilderSpec.groovy | 67 +++++++++++++++++++ .../util/JsonToJsonPathsConverterSpec.groovy | 42 ++++++++++++ 3 files changed, 116 insertions(+), 1 deletion(-) diff --git a/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/util/JsonToJsonPathsConverter.groovy b/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/util/JsonToJsonPathsConverter.groovy index b868ab161a..1bfe6bf92c 100644 --- a/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/util/JsonToJsonPathsConverter.groovy +++ b/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/util/JsonToJsonPathsConverter.groovy @@ -38,6 +38,7 @@ import java.util.regex.Pattern * JSON Paths together with methods needed to be called to build them. * * @author Marcin Grzejszczak + * @author Tim Ysewyn */ @Slf4j class JsonToJsonPathsConverter { @@ -232,8 +233,10 @@ class JsonToJsonPathsConverter { return convertWithKey(List, key, value as Map, closure) } else if (isAnEntryWithoutNestedStructures(value)) { return convertWithKey(List, key, value as Map, closure) - } else if (value instanceof Map) { + } else if (value instanceof Map && !value.isEmpty()) { return convertWithKey(Map, key, value as Map, closure) + } else if (value instanceof Map && value.isEmpty()) { + return runClosure(closure, key.isEmpty(), value) // JSON with a list of primitives ["a", "b", "c"] in root issue #266 } else if (key.isIteratingOverNamelessArray() && value instanceof List && listContainsOnlyPrimitives(value)) { addSizeVerificationForListWithPrimitives(key, closure, value) @@ -356,6 +359,9 @@ class JsonToJsonPathsConverter { return false } Map valueAsMap = ((Map) value) + if (valueAsMap.isEmpty()) { + return false + } return valueAsMap.entrySet().every { Map.Entry entry -> [String, Number, Boolean].any { it.isAssignableFrom(entry.value.getClass()) } } diff --git a/spring-cloud-contract-verifier/src/test/groovy/org/springframework/cloud/contract/verifier/builder/MockMvcMethodBodyBuilderSpec.groovy b/spring-cloud-contract-verifier/src/test/groovy/org/springframework/cloud/contract/verifier/builder/MockMvcMethodBodyBuilderSpec.groovy index cff968bd6a..227a0b5a8f 100644 --- a/spring-cloud-contract-verifier/src/test/groovy/org/springframework/cloud/contract/verifier/builder/MockMvcMethodBodyBuilderSpec.groovy +++ b/spring-cloud-contract-verifier/src/test/groovy/org/springframework/cloud/contract/verifier/builder/MockMvcMethodBodyBuilderSpec.groovy @@ -2562,4 +2562,71 @@ DocumentContext parsedJson = JsonPath.parse(json); SyntaxChecker.tryToCompile("MockMvcSpockMethodRequestProcessingBodyBuilder", blockBuilder.toString()) } + @Issue("#628") + def "should execute method in response header [#methodBuilderName]"() { + given: + Contract contractDsl = Contract.make { + request { + method 'GET' + urlPath '/whatever' + headers { + header 'My-UUID': value(test(execute('property("my-uuid")')), stub('76c53386-ad9b-11e6-92dc-0370ae47c3b2')) + } + } + response { + status 200 + headers { + header 'My-UUID': value(test(execute('property("my-uuid")')), stub('76c53386-ad9b-11e6-92dc-0370ae47c3b2')) + } + } + } + MethodBodyBuilder builder = methodBuilder(contractDsl) + BlockBuilder blockBuilder = new BlockBuilder(" ") + when: + builder.appendTo(blockBuilder) + String test = blockBuilder.toString() + then: + responseAssertion(test) + where: + methodBuilderName | methodBuilder | responseAssertion + "MockMvcSpockMethodBuilder" | { Contract dsl -> new MockMvcSpockMethodRequestProcessingBodyBuilder(dsl, properties) } | { String body -> body.contains("response.header('My-UUID') == property(\"my-uuid\")") } + "MockMvcJUnitMethodBuilder" | { Contract dsl -> new MockMvcJUnitMethodBodyBuilder(dsl, properties) } | { String body -> body.contains('assertThat(response.header("My-UUID")).isEqualTo(property("my-uuid"));') } + "JaxRsClientSpockMethodRequestProcessingBodyBuilder" | { Contract dsl -> new JaxRsClientSpockMethodRequestProcessingBodyBuilder(dsl, properties) } | { String body -> body.contains("response.getHeaderString('My-UUID') == property(\"my-uuid\")") } + "JaxRsClientJUnitMethodBodyBuilder" | { Contract dsl -> new JaxRsClientJUnitMethodBodyBuilder(dsl, properties) } | { String body -> body.contains('assertThat(response.getHeaderString("My-UUID")).isEqualTo(property("my-uuid"));') } + } + + @Issue('#554') + def "should create an assertion for an empty map or Object for [#methodBuilderName]"() { + given: + Contract contractDsl = Contract.make { + request { + method 'GET' + url '/api/v1/xxxx' + } + response { + status 200 + body([ + aMap: ["foo": "bar"], + anEmptyMap: [:] + ]) + } + } + MethodBodyBuilder builder = methodBuilder(contractDsl) + BlockBuilder blockBuilder = new BlockBuilder(" ") + and: + builder.appendTo(blockBuilder) + String test = blockBuilder.toString() + when: + SyntaxChecker.tryToRun(methodBuilderName, test.join("\n")) + then: + test.contains('''assertThatJson(parsedJson).field("['aMap']").field("['foo']").isEqualTo("bar")''') + test.contains('''assertThatJson(parsedJson).field("['anEmptyMap']").isEmpty()''') + where: + methodBuilderName | methodBuilder + "MockMvcSpockMethodBuilder" | { Contract dsl -> new MockMvcSpockMethodRequestProcessingBodyBuilder(dsl, properties) } + "MockMvcJUnitMethodBuilder" | { Contract dsl -> new MockMvcJUnitMethodBodyBuilder(dsl, properties) } + "JaxRsClientSpockMethodRequestProcessingBodyBuilder" | { Contract dsl -> new JaxRsClientSpockMethodRequestProcessingBodyBuilder(dsl, properties) } + "JaxRsClientJUnitMethodBodyBuilder" | { Contract dsl -> new JaxRsClientJUnitMethodBodyBuilder(dsl, properties) } + } + } diff --git a/spring-cloud-contract-verifier/src/test/groovy/org/springframework/cloud/contract/verifier/util/JsonToJsonPathsConverterSpec.groovy b/spring-cloud-contract-verifier/src/test/groovy/org/springframework/cloud/contract/verifier/util/JsonToJsonPathsConverterSpec.groovy index 06cc215abc..b4661572fb 100644 --- a/spring-cloud-contract-verifier/src/test/groovy/org/springframework/cloud/contract/verifier/util/JsonToJsonPathsConverterSpec.groovy +++ b/spring-cloud-contract-verifier/src/test/groovy/org/springframework/cloud/contract/verifier/util/JsonToJsonPathsConverterSpec.groovy @@ -842,6 +842,48 @@ class JsonToJsonPathsConverterSpec extends Specification { e.message.contains("not found") } + def "should generate assertion for empty map"() { + given: + Map json = [ + aMap: ["foo": "bar"], + anEmptyMap: [:] + ] + when: + JsonPaths pathAndValues = new JsonToJsonPathsConverter().transformToJsonPathWithTestsSideValues(json) + then: + pathAndValues.find { + it.method() == """.field("['aMap']").field("['foo']").isEqualTo("bar")""" && + it.jsonPath() == """\$.['aMap'][?(@.['foo'] == 'bar')]""" + } + pathAndValues.find { + it.method()== """.field("['anEmptyMap']").isEmpty()""" && + it.jsonPath() == """\$.['anEmptyMap']""" + } + and: + pathAndValues.size() == 2 + } + + def "should generate assertion for empty object"() { + given: + String json = """{ + "aMap": {"foo": "bar"}, + "anEmptyMap": {} + }""" + when: + JsonPaths pathAndValues = new JsonToJsonPathsConverter().transformToJsonPathWithTestsSideValues(new JsonSlurper().parseText(json)) + then: + pathAndValues.find { + it.method()== """.field("['aMap']").field("['foo']").isEqualTo("bar")""" && + it.jsonPath() == """\$.['aMap'][?(@.['foo'] == 'bar')]""" + } + pathAndValues.find { + it.method() == """.field("['anEmptyMap']").isEmpty()""" && + it.jsonPath() == """\$.['anEmptyMap']""" + } + and: + pathAndValues.size() == 2 + } + private BodyMatcher matcher(final MatchingType matchingType, final String jsonPath, final Object value) { return new BodyMatcher() { @Override From 077e18aa259e9ac0999d4435c056a3fca56a127f Mon Sep 17 00:00:00 2001 From: Tim Ysewyn Date: Wed, 9 May 2018 07:57:30 +0200 Subject: [PATCH 3/3] A response header should be verified against an execution property (#649) Fixes #628 --- .../JUnitMessagingMethodBodyBuilder.groovy | 2 +- .../JaxRsClientJUnitMethodBodyBuilder.groovy | 2 +- ...kMethodRequestProcessingBodyBuilder.groovy | 2 +- ...kMethodRequestProcessingBodyBuilder.groovy | 2 +- .../RestAssuredJUnitMethodBodyBuilder.groovy | 2 +- .../SpockMessagingMethodBodyBuilder.groovy | 2 +- .../MessagingMethodBodyBuilderSpec.groovy | 36 +++++++++++++++++++ .../MockMvcMethodBodyBuilderSpec.groovy | 34 ------------------ 8 files changed, 42 insertions(+), 40 deletions(-) diff --git a/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/builder/JUnitMessagingMethodBodyBuilder.groovy b/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/builder/JUnitMessagingMethodBodyBuilder.groovy index 902aa99911..f0a7687e8a 100644 --- a/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/builder/JUnitMessagingMethodBodyBuilder.groovy +++ b/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/builder/JUnitMessagingMethodBodyBuilder.groovy @@ -112,7 +112,7 @@ class JUnitMessagingMethodBodyBuilder extends MessagingMethodBodyBuilder { @Override protected void processHeaderElement(BlockBuilder blockBuilder, String property, ExecutionProperty exec) { blockBuilder.addLine("assertThat(response.getHeader(\"$property\")).isNotNull();") - blockBuilder.addLine("${exec.insertValue("response.getHeader(\"$property\").toString()")};") + blockBuilder.addLine("assertThat(response.getHeader(\"$property\")).isEqualTo(${exec.insertValue("response.getHeader(\"$property\").toString()")});") } @Override diff --git a/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/builder/JaxRsClientJUnitMethodBodyBuilder.groovy b/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/builder/JaxRsClientJUnitMethodBodyBuilder.groovy index 47bd2eda22..8d7613466e 100644 --- a/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/builder/JaxRsClientJUnitMethodBodyBuilder.groovy +++ b/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/builder/JaxRsClientJUnitMethodBodyBuilder.groovy @@ -203,7 +203,7 @@ class JaxRsClientJUnitMethodBodyBuilder extends JUnitMethodBodyBuilder { @Override protected void processHeaderElement(BlockBuilder blockBuilder, String property, ExecutionProperty exec) { - blockBuilder.addLine("${exec.insertValue("response.getHeaderString(\"$property\")")};") + blockBuilder.addLine("assertThat(response.getHeaderString(\"$property\")).isEqualTo(${exec.insertValue("response.getHeaderString(\"$property\")")});") } @Override diff --git a/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/builder/JaxRsClientSpockMethodRequestProcessingBodyBuilder.groovy b/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/builder/JaxRsClientSpockMethodRequestProcessingBodyBuilder.groovy index a6e7327a20..7cc5a5b710 100644 --- a/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/builder/JaxRsClientSpockMethodRequestProcessingBodyBuilder.groovy +++ b/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/builder/JaxRsClientSpockMethodRequestProcessingBodyBuilder.groovy @@ -184,7 +184,7 @@ class JaxRsClientSpockMethodRequestProcessingBodyBuilder extends SpockMethodRequ @Override protected void processHeaderElement(BlockBuilder blockBuilder, String property, ExecutionProperty exec) { - blockBuilder.addLine("${exec.insertValue("response.getHeaderString(\'$property\')")}") + blockBuilder.addLine("response.getHeaderString(\'$property\') == ${exec.insertValue("response.getHeaderString(\'$property\')")}") } @Override diff --git a/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/builder/MockMvcSpockMethodRequestProcessingBodyBuilder.groovy b/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/builder/MockMvcSpockMethodRequestProcessingBodyBuilder.groovy index 45f475d49e..37807b3a13 100644 --- a/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/builder/MockMvcSpockMethodRequestProcessingBodyBuilder.groovy +++ b/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/builder/MockMvcSpockMethodRequestProcessingBodyBuilder.groovy @@ -96,7 +96,7 @@ class MockMvcSpockMethodRequestProcessingBodyBuilder extends SpockMethodRequestP @Override protected void processHeaderElement(BlockBuilder blockBuilder, String property, ExecutionProperty exec) { - blockBuilder.addLine("${exec.insertValue("response.header(\'$property\')")}") + blockBuilder.addLine("response.header(\'$property\') == ${exec.insertValue("response.header(\'$property\')")}") } @Override diff --git a/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/builder/RestAssuredJUnitMethodBodyBuilder.groovy b/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/builder/RestAssuredJUnitMethodBodyBuilder.groovy index 51294f1160..fdfabf0c72 100644 --- a/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/builder/RestAssuredJUnitMethodBodyBuilder.groovy +++ b/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/builder/RestAssuredJUnitMethodBodyBuilder.groovy @@ -103,7 +103,7 @@ class RestAssuredJUnitMethodBodyBuilder extends JUnitMethodBodyBuilder { @Override protected void processHeaderElement(BlockBuilder blockBuilder, String property, ExecutionProperty exec) { - blockBuilder.addLine("${exec.insertValue("response.header(\"$property\")")};") + blockBuilder.addLine("assertThat(response.header(\"$property\")).isEqualTo(${exec.insertValue("response.header(\"$property\")")});") } @Override diff --git a/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/builder/SpockMessagingMethodBodyBuilder.groovy b/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/builder/SpockMessagingMethodBodyBuilder.groovy index 1c2777587d..81bbcfc49e 100644 --- a/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/builder/SpockMessagingMethodBodyBuilder.groovy +++ b/spring-cloud-contract-verifier/src/main/groovy/org/springframework/cloud/contract/verifier/builder/SpockMessagingMethodBodyBuilder.groovy @@ -80,7 +80,7 @@ class SpockMessagingMethodBodyBuilder extends MessagingMethodBodyBuilder { @Override protected void processHeaderElement(BlockBuilder blockBuilder, String property, ExecutionProperty exec) { - blockBuilder.addLine("${exec.insertValue("response.getHeader(\'$property\')?.toString()")}") + blockBuilder.addLine("response.getHeader('$property') == ${exec.insertValue("response.getHeader(\'$property\')?.toString()")}") } @Override diff --git a/spring-cloud-contract-verifier/src/test/groovy/org/springframework/cloud/contract/verifier/builder/MessagingMethodBodyBuilderSpec.groovy b/spring-cloud-contract-verifier/src/test/groovy/org/springframework/cloud/contract/verifier/builder/MessagingMethodBodyBuilderSpec.groovy index f1b158bfe0..edcc5a411c 100644 --- a/spring-cloud-contract-verifier/src/test/groovy/org/springframework/cloud/contract/verifier/builder/MessagingMethodBodyBuilderSpec.groovy +++ b/spring-cloud-contract-verifier/src/test/groovy/org/springframework/cloud/contract/verifier/builder/MessagingMethodBodyBuilderSpec.groovy @@ -853,4 +853,40 @@ Contract.make { ''' } + @Issue("#628") + def "should execute method in response header [#methodBuilderName]"() { + given: + Contract contractDsl = Contract.make { + label 'shouldPublishMessage' + // input to the contract + input { + // the contract will be triggered by a method + triggeredBy('foo()') + } + // output message of the contract + outputMessage { + // destination to which the output message will be sent + sentTo('messageExchange') + // the body of the output message + body([ + "field": "value" + ]) + headers { + header 'My-UUID': value(test(execute('property("my-uuid")')), stub('76c53386-ad9b-11e6-92dc-0370ae47c3b2')) + } + } + } + MethodBodyBuilder builder = methodBuilder(contractDsl) + BlockBuilder blockBuilder = new BlockBuilder(" ") + when: + builder.appendTo(blockBuilder) + String test = blockBuilder.toString() + then: + responseAssertion(test) + where: + methodBuilderName | methodBuilder | responseAssertion + "SpockMessagingMethodBodyBuilder" | { Contract dsl -> new SpockMessagingMethodBodyBuilder(dsl, properties) } | { String body -> body.contains("response.getHeader('My-UUID') == property(\"my-uuid\")") } + "JUnitMessagingMethodBodyBuilder" | { Contract dsl -> new JUnitMessagingMethodBodyBuilder(dsl, properties) } | { String body -> body.contains('assertThat(response.getHeader("My-UUID")).isEqualTo(property("my-uuid"));') } + } + } diff --git a/spring-cloud-contract-verifier/src/test/groovy/org/springframework/cloud/contract/verifier/builder/MockMvcMethodBodyBuilderSpec.groovy b/spring-cloud-contract-verifier/src/test/groovy/org/springframework/cloud/contract/verifier/builder/MockMvcMethodBodyBuilderSpec.groovy index 227a0b5a8f..b06594888c 100644 --- a/spring-cloud-contract-verifier/src/test/groovy/org/springframework/cloud/contract/verifier/builder/MockMvcMethodBodyBuilderSpec.groovy +++ b/spring-cloud-contract-verifier/src/test/groovy/org/springframework/cloud/contract/verifier/builder/MockMvcMethodBodyBuilderSpec.groovy @@ -2595,38 +2595,4 @@ DocumentContext parsedJson = JsonPath.parse(json); "JaxRsClientJUnitMethodBodyBuilder" | { Contract dsl -> new JaxRsClientJUnitMethodBodyBuilder(dsl, properties) } | { String body -> body.contains('assertThat(response.getHeaderString("My-UUID")).isEqualTo(property("my-uuid"));') } } - @Issue('#554') - def "should create an assertion for an empty map or Object for [#methodBuilderName]"() { - given: - Contract contractDsl = Contract.make { - request { - method 'GET' - url '/api/v1/xxxx' - } - response { - status 200 - body([ - aMap: ["foo": "bar"], - anEmptyMap: [:] - ]) - } - } - MethodBodyBuilder builder = methodBuilder(contractDsl) - BlockBuilder blockBuilder = new BlockBuilder(" ") - and: - builder.appendTo(blockBuilder) - String test = blockBuilder.toString() - when: - SyntaxChecker.tryToRun(methodBuilderName, test.join("\n")) - then: - test.contains('''assertThatJson(parsedJson).field("['aMap']").field("['foo']").isEqualTo("bar")''') - test.contains('''assertThatJson(parsedJson).field("['anEmptyMap']").isEmpty()''') - where: - methodBuilderName | methodBuilder - "MockMvcSpockMethodBuilder" | { Contract dsl -> new MockMvcSpockMethodRequestProcessingBodyBuilder(dsl, properties) } - "MockMvcJUnitMethodBuilder" | { Contract dsl -> new MockMvcJUnitMethodBodyBuilder(dsl, properties) } - "JaxRsClientSpockMethodRequestProcessingBodyBuilder" | { Contract dsl -> new JaxRsClientSpockMethodRequestProcessingBodyBuilder(dsl, properties) } - "JaxRsClientJUnitMethodBodyBuilder" | { Contract dsl -> new JaxRsClientJUnitMethodBodyBuilder(dsl, properties) } - } - }