Merge pull request #198 from Codearte/feature/#16-real-support-for-JUnit-new

Feature/#16 real support for junit new
This commit is contained in:
Olga Maciaszek-Sharma
2016-02-24 00:04:32 +01:00
35 changed files with 2680 additions and 1773 deletions

View File

@@ -15,7 +15,7 @@ import static io.codearte.accurest.util.NamesUtil.capitalize
@Slf4j
class SingleTestGenerator {
private static final String JSON_ASSERT_STATIC_IMPORT = 'com.blogspot.toomuchcoding.jsonassert.JsonAssertion.assertThat'
private static final String JSON_ASSERT_STATIC_IMPORT = 'com.blogspot.toomuchcoding.jsonassert.JsonAssertion.assertThatJson'
private static final String JSON_ASSERT_CLASS = 'com.blogspot.toomuchcoding.jsonassert.JsonAssertion'
private final AccurestConfigProperties configProperties
@@ -51,6 +51,9 @@ class SingleTestGenerator {
if (configProperties.testMode == TestMode.JAXRSCLIENT) {
clazz.addStaticImport('javax.ws.rs.client.Entity.*')
if (configProperties.targetFramework == TestFramework.JUNIT) {
clazz.addImport('javax.ws.rs.core.Response')
}
} else if (configProperties.testMode == TestMode.MOCKMVC) {
clazz.addStaticImport('com.jayway.restassured.module.mockmvc.RestAssuredMockMvc.*')
} else {
@@ -58,9 +61,12 @@ class SingleTestGenerator {
}
if (configProperties.targetFramework == TestFramework.JUNIT) {
if (configProperties.testMode == TestMode.MOCKMVC) {
clazz.addImport('com.jayway.restassured.module.mockmvc.specification.MockMvcRequestSpecification')
clazz.addImport('com.jayway.restassured.response.ResponseOptions')
}
clazz.addImport('org.junit.Test')
} else {
clazz.addImport('groovy.json.JsonSlurper')
clazz.addStaticImport('org.assertj.core.api.Assertions.assertThat')
}
if (configProperties.ruleClassForTests) {

View File

@@ -62,6 +62,17 @@ class BlockBuilder {
return this
}
BlockBuilder addAtTheEnd(String toAdd) {
if (builder.charAt(builder.length() - 1) as String == '\n') {
builder.replace(builder.length() - 1, builder.length(), toAdd)
builder << '\n'
} else {
builder << toAdd
}
return this
}
@Override
String toString() {
return builder.toString()

View File

@@ -1,18 +1,116 @@
package io.codearte.accurest.builder
import groovy.json.StringEscapeUtils
import groovy.transform.PackageScope
import groovy.transform.TypeChecked
import io.codearte.accurest.dsl.GroovyDsl
import io.codearte.accurest.dsl.internal.ExecutionProperty
import io.codearte.accurest.dsl.internal.Header
import io.codearte.accurest.dsl.internal.NamedProperty
import io.codearte.accurest.dsl.internal.Request
import static groovy.json.StringEscapeUtils.escapeJava
import static io.codearte.accurest.config.TestFramework.JUNIT
import static io.codearte.accurest.util.ContentUtils.getJavaMultipartFileParameterContent
/**
* @author Jakub Kubrynski
* @author Olga Maciaszek-Sharma
*/
class JUnitMethodBodyBuilder {
/*
given()
.contentType("application/json")
.header("Accept", "application/json")
.body("{'name': 'MyApp', 'description' : 'awesome app'}".replaceAll("'", "\"")).
@TypeChecked
@PackageScope
abstract class JUnitMethodBodyBuilder extends MethodBodyBuilder {
expect()
.statusCode(200).body("id", is(not(nullValue()))).
JUnitMethodBodyBuilder(GroovyDsl stubDefinition) {
super(stubDefinition)
}
when()
.post(root.toString() + "rest/applications").asString();*/
@Override
protected String getResponseAsString() {
return "response.getBody().asString()"
}
@Override
protected String addCommentSignIfRequired(String baseString) {
return "// $baseString"
}
@Override
protected BlockBuilder addColonIfRequired(BlockBuilder blockBuilder) {
blockBuilder.addAtTheEnd(JUNIT.lineSuffix)
return blockBuilder
}
@Override
protected String getResponseBodyPropertyComparisonString(String property, String value) {
return "assertThat(responseBody${property}).isEqualTo(\"${value}\")"
}
@Override
protected void processBodyElement(BlockBuilder blockBuilder, String property, ExecutionProperty exec) {
blockBuilder.addLine("${exec.insertValue("parsedJson.read(\"\\\$$property\")")};")
}
@Override
protected String getPropertyInListString(String property, Integer listIndex) {
return "${property}.get($listIndex)" ?: ''
}
@Override
protected String convertUnicodeEscapesIfRequired(String json) {
String unescapedJson = StringEscapeUtils.unescapeJavaScript(json)
return escapeJava(unescapedJson)
}
@Override
protected void processBodyElement(BlockBuilder blockBuilder, String property, Map.Entry entry) {
processBodyElement(blockBuilder, property + getMapKeyReferenceString(entry), entry.value)
}
private String getMapKeyReferenceString(Map.Entry entry) {
if (entry.value instanceof ExecutionProperty) {
return "." + entry.key
}
return """.get(\\\"$entry.key\\\")"""
}
@Override
protected String getParsedXmlResponseBodyString(String responseString) {
return "Object responseBody = new XmlSlurper().parseText($responseString);"
}
@Override
protected String getSimpleResponseBodyString(String responseString) {
return "Object responseBody = ($responseString);"
}
@Override
protected String getResponseString(Request request) {
return 'ResponseOptions response = given().spec(request)'
}
@Override
protected String getRequestString() {
return 'MockMvcRequestSpecification request = given()'
}
@Override
protected String getHeaderString(Header header) {
return ".header(\"${getTestSideValue(header.name)}\", \"${getTestSideValue(header.serverValue)}\")"
}
@Override
protected String getBodyString(String bodyAsString) {
return ".body(\"$bodyAsString\")"
}
@Override
protected String getMultipartFileParameterContent(String propertyName, NamedProperty propertyValue) {
return getJavaMultipartFileParameterContent(propertyName, propertyValue)
}
@Override
protected String getParameterString(Map.Entry<String, Object> parameter) {
return """.param("${escapeJava(parameter.key)}", "${escapeJava(parameter.value as String)}")"""
}
}

View File

@@ -0,0 +1,110 @@
package io.codearte.accurest.builder
import io.codearte.accurest.dsl.GroovyDsl
import io.codearte.accurest.dsl.internal.Header
import io.codearte.accurest.dsl.internal.QueryParameter
import io.codearte.accurest.dsl.internal.QueryParameters
import static io.codearte.accurest.config.TestFramework.JUNIT
/**
* @author Olga Maciaszek-Sharma
@since 21.02.16
*/
class JaxRsClientJUnitMethodBodyBuilder extends JUnitMethodBodyBuilder {
JaxRsClientJUnitMethodBodyBuilder(GroovyDsl stubDefinition) {
super(stubDefinition)
}
@Override
protected void given(BlockBuilder bb) {}
@Override
protected void givenBlock(BlockBuilder bb) {
}
@Override
protected void when(BlockBuilder bb) {
bb.addLine("Response response = webTarget")
bb.indent()
appendUrlPathAndQueryParameters(bb)
appendRequestWithRequiredResponseContentType(bb)
appendHeaders(bb)
appendMethodAndBody(bb)
bb.addAtTheEnd(JUNIT.lineSuffix)
bb.unindent()
bb.addEmptyLine()
bb.addLine("String responseAsString = response.readEntity(String.class);")
}
protected void appendUrlPathAndQueryParameters(BlockBuilder bb) {
if (request.url) {
bb.addLine(".path(\"$request.url.serverValue\")")
appendQueryParams(request.url.queryParameters, bb)
} else if (request.urlPath) {
bb.addLine(".path(\"$request.urlPath.serverValue\")")
appendQueryParams(request.urlPath.queryParameters, bb)
}
}
private void appendQueryParams(QueryParameters queryParameters, BlockBuilder bb) {
if (!queryParameters?.parameters) {
return
}
queryParameters.parameters.findAll(this.&allowedQueryParameter).each { QueryParameter param ->
bb.addLine(".queryParam(\"$param.name\", \"${resolveParamValue(param).toString()}\")")
}
}
protected void appendMethodAndBody(BlockBuilder bb) {
String method = request.method.serverValue.toString().toLowerCase()
if (request.body) {
String contentType = getHeader('Content-Type') ?: getRequestContentType().mimeType
bb.addLine(".method(\"${method.toUpperCase()}\", entity(\"$bodyAsString\", \"$contentType\"))")
} else {
bb.addLine(".method(\"${method.toUpperCase()}\")")
}
}
protected appendHeaders(BlockBuilder bb) {
request.headers?.collect { Header header ->
if (header.name == 'Content-Type' || header.name == 'Accept') return
bb.addLine(".header(\"${header.name}\", \"${header.serverValue}\")")
}
}
protected void appendRequestWithRequiredResponseContentType(BlockBuilder bb) {
String acceptHeader = getHeader("Accept")
if (acceptHeader) {
bb.addLine(".request(\"$acceptHeader\")")
} else {
bb.addLine(".request()")
}
}
@Override
protected void validateResponseCodeBlock(BlockBuilder bb) {
bb.addLine("assertThat(response.getStatus()).isEqualTo($response.status.serverValue);")
}
@Override
protected void validateResponseHeadersBlock(BlockBuilder bb) {
response.headers?.collect { Header header ->
bb.addLine("assertThat(response.getHeaderString(\"$header.name\")).isEqualTo(\"$header.serverValue\");")
}
}
protected String getHeader(String name) {
return request.headers?.entries.find { it.name == name }?.serverValue
}
@Override
protected String getResponseAsString() {
return 'responseAsString'
}
}

View File

@@ -1,4 +1,5 @@
package io.codearte.accurest.builder
import groovy.transform.PackageScope
import groovy.transform.TypeChecked
import io.codearte.accurest.dsl.GroovyDsl
@@ -14,6 +15,9 @@ class JaxRsClientSpockMethodBodyBuilder extends SpockMethodBodyBuilder {
super(stubDefinition)
}
@Override
protected void given(BlockBuilder bb) {}
@Override
protected void givenBlock(BlockBuilder bb) {
}

View File

@@ -0,0 +1,310 @@
package io.codearte.accurest.builder
import groovy.json.JsonOutput
import groovy.transform.PackageScope
import groovy.transform.TypeChecked
import groovy.transform.TypeCheckingMode
import io.codearte.accurest.dsl.GroovyDsl
import io.codearte.accurest.dsl.internal.DslProperty
import io.codearte.accurest.dsl.internal.ExecutionProperty
import io.codearte.accurest.dsl.internal.Header
import io.codearte.accurest.dsl.internal.MatchingStrategy
import io.codearte.accurest.dsl.internal.NamedProperty
import io.codearte.accurest.dsl.internal.QueryParameter
import io.codearte.accurest.dsl.internal.Request
import io.codearte.accurest.dsl.internal.Response
import io.codearte.accurest.dsl.internal.Url
import io.codearte.accurest.util.ContentType
import io.codearte.accurest.util.JsonPaths
import io.codearte.accurest.util.JsonToJsonPathsConverter
import io.codearte.accurest.util.MapConverter
import static io.codearte.accurest.util.ContentUtils.extractValue
import static io.codearte.accurest.util.ContentUtils.recognizeContentTypeFromContent
import static io.codearte.accurest.util.ContentUtils.recognizeContentTypeFromHeader
/**
* @author Olga Maciaszek-Sharma
* @since 2016-02-17
*/
@TypeChecked
@PackageScope
abstract class MethodBodyBuilder {
protected final Request request
protected final Response response
MethodBodyBuilder(GroovyDsl stubDefinition) {
this.request = stubDefinition.request
this.response = stubDefinition.response
}
protected abstract void validateResponseCodeBlock(BlockBuilder bb)
protected abstract void validateResponseHeadersBlock(BlockBuilder bb)
protected abstract String getResponseAsString()
protected abstract String addCommentSignIfRequired(String baseString)
protected abstract BlockBuilder addColonIfRequired(BlockBuilder blockBuilder)
protected abstract String getResponseBodyPropertyComparisonString(String property, String value)
protected abstract void processBodyElement(BlockBuilder blockBuilder, String property, ExecutionProperty exec)
protected abstract void processBodyElement(BlockBuilder blockBuilder, String property, Map.Entry entry)
protected abstract String getPropertyInListString(String property, Integer index)
protected abstract String convertUnicodeEscapesIfRequired(String json)
protected abstract String getParsedXmlResponseBodyString(String responseString)
protected abstract String getSimpleResponseBodyString(String responseString)
protected abstract String getResponseString(Request request)
protected abstract String getRequestString()
protected abstract String getHeaderString(Header header)
protected abstract String getBodyString(String bodyAsString)
protected abstract String getMultipartFileParameterContent(String propertyName, NamedProperty propertyValue)
protected abstract String getParameterString(Map.Entry<String, Object> parameter)
void appendTo(BlockBuilder blockBuilder) {
blockBuilder.startBlock()
givenBlock(blockBuilder)
whenBlock(blockBuilder)
thenBlock(blockBuilder)
blockBuilder.endBlock()
}
protected void thenBlock(BlockBuilder bb) {
bb.addLine(addCommentSignIfRequired('then:'))
bb.startBlock()
then(bb)
bb.endBlock()
}
protected void whenBlock(BlockBuilder bb) {
bb.addLine(addCommentSignIfRequired('when:'))
bb.startBlock()
when(bb)
bb.endBlock().addEmptyLine()
}
protected void givenBlock(BlockBuilder bb) {
bb.addLine(addCommentSignIfRequired('given:'))
bb.startBlock()
given(bb)
bb.endBlock().addEmptyLine()
}
protected void given(BlockBuilder bb) {
bb.addLine(getRequestString())
bb.indent()
request.headers?.collect { Header header ->
bb.addLine(getHeaderString(header))
}
if (request.body) {
bb.addLine(getBodyString(bodyAsString))
}
if (request.multipart) {
multipartParameters?.each { Map.Entry<String, Object> entry -> bb.addLine(getMultipartParameterLine(entry)) }
}
addColonIfRequired(bb)
bb.unindent()
}
protected void when(BlockBuilder bb) {
bb.addLine(getResponseString(request))
bb.indent()
String url = buildUrl(request)
String method = request.method.serverValue.toString().toLowerCase()
bb.addLine(/.${method}("$url")/)
addColonIfRequired(bb)
bb.unindent()
}
protected void then(BlockBuilder bb) {
validateResponseCodeBlock(bb)
if (response.headers) {
validateResponseHeadersBlock(bb)
}
if (response.body) {
bb.endBlock()
bb.addLine(addCommentSignIfRequired('and:')).startBlock()
validateResponseBodyBlock(bb)
}
}
private void validateResponseBodyBlock(BlockBuilder bb) {
def responseBody = response.body.serverValue
ContentType contentType = getResponseContentType()
if (responseBody instanceof GString) {
responseBody = extractValue(responseBody, contentType, { DslProperty dslProperty -> dslProperty.serverValue })
}
if (contentType == ContentType.JSON) {
appendJsonPath(bb, getResponseAsString())
JsonPaths jsonPaths = JsonToJsonPathsConverter.transformToJsonPathWithTestsSideValues(responseBody)
jsonPaths.each {
bb.addLine("assertThatJson(parsedJson)" + it.method())
addColonIfRequired(bb)
}
processBodyElement(bb, "", responseBody)
} else if (contentType == ContentType.XML) {
bb.addLine(getParsedXmlResponseBodyString(getResponseAsString()))
addColonIfRequired(bb)
// TODO xml validation
} else {
bb.addLine(getSimpleResponseBodyString(getResponseAsString()))
processText(bb, "", responseBody as String)
addColonIfRequired(bb)
}
}
private ContentType getResponseContentType() {
ContentType contentType = recognizeContentTypeFromHeader(response.headers)
if (contentType == ContentType.UNKNOWN) {
contentType = recognizeContentTypeFromContent(response.body.serverValue)
}
return contentType
}
protected void appendJsonPath(BlockBuilder blockBuilder, String json) {
blockBuilder.addLine(("DocumentContext parsedJson = JsonPath.parse($json)"))
addColonIfRequired(blockBuilder)
}
protected void processText(BlockBuilder blockBuilder, String property, String value) {
if (value.startsWith('$')) {
value = stripFirstChar(value).replaceAll('\\$value', "responseBody$property")
blockBuilder.addLine(value)
addColonIfRequired(blockBuilder)
} else {
blockBuilder.addLine(getResponseBodyPropertyComparisonString(property, value))
}
}
private String stripFirstChar(String s) {
return s.substring(1);
}
protected void processBodyElement(BlockBuilder blockBuilder, String property, Object value) {
}
protected String getBodyAsString() {
Object bodyValue = extractServerValueFromBody(request.body.serverValue)
String json = new JsonOutput().toJson(bodyValue)
json = convertUnicodeEscapesIfRequired(json)
return trimRepeatedQuotes(json)
}
protected Map<String, Object> getMultipartParameters() {
return (Map<String, Object>) request?.multipart?.serverValue
}
protected String trimRepeatedQuotes(String toTrim) {
return toTrim.startsWith('"') ? toTrim.replaceAll('"', '') : toTrim
}
protected Object extractServerValueFromBody(bodyValue) {
if (bodyValue instanceof GString) {
bodyValue = extractValue(bodyValue, { DslProperty dslProperty -> dslProperty.serverValue })
} else {
bodyValue = MapConverter.transformValues(bodyValue, { it instanceof DslProperty ? it.serverValue : it })
}
return bodyValue
}
protected boolean allowedQueryParameter(QueryParameter param) {
return allowedQueryParameter(param.serverValue)
}
protected boolean allowedQueryParameter(MatchingStrategy matchingStrategy) {
return matchingStrategy.type != MatchingStrategy.Type.ABSENT
}
protected boolean allowedQueryParameter(Object o) {
return true
}
protected String resolveParamValue(QueryParameter param) {
return resolveParamValue(param.serverValue)
}
protected String resolveParamValue(Object value) {
return value.toString()
}
protected String resolveParamValue(MatchingStrategy matchingStrategy) {
return matchingStrategy.serverValue.toString()
}
protected ContentType getRequestContentType() {
ContentType contentType = recognizeContentTypeFromHeader(request.headers)
if (contentType == ContentType.UNKNOWN) {
contentType = recognizeContentTypeFromContent(request.body.serverValue)
}
return contentType
}
protected String getTestSideValue(Object object) {
return MapConverter.getTestSideValues(object).toString()
}
protected void processBodyElement(BlockBuilder blockBuilder, String property, Map map) {
map.each {
processBodyElement(blockBuilder, property, it)
}
}
protected void processBodyElement(BlockBuilder blockBuilder, String property, List list) {
list.eachWithIndex { listElement, listIndex ->
String prop = getPropertyInListString(property, listIndex as Integer)
processBodyElement(blockBuilder, prop, listElement)
}
}
protected String buildUrl(Request request) {
if (request.url)
return getTestSideValue(buildUrlFromUrlPath(request.url))
if (request.urlPath)
return getTestSideValue(buildUrlFromUrlPath(request.urlPath))
throw new IllegalStateException("URL is not set!")
}
@TypeChecked(TypeCheckingMode.SKIP)
protected String buildUrlFromUrlPath(Url url) {
if (hasQueryParams(url)) {
String params = url.queryParameters.parameters
.findAll(this.&allowedQueryParameter)
.inject([] as List<String>) { List<String> result, QueryParameter param ->
result << "${param.name}=${resolveParamValue(param).toString()}"
}
.join('&')
return "${MapConverter.getTestSideValues(url.serverValue)}?$params"
}
return MapConverter.getTestSideValues(url.serverValue)
}
protected String getMultipartParameterLine(Map.Entry<String, Object> parameter) {
if (parameter.value instanceof NamedProperty) {
return ".multiPart(${getMultipartFileParameterContent(parameter.key, (NamedProperty) parameter.value)})"
}
return getParameterString(parameter)
}
private boolean hasQueryParams(Url url) {
return url.queryParameters
}
}

View File

@@ -48,8 +48,14 @@ class MethodBuilder {
blockBuilder.addLine('}')
}
private SpockMethodBodyBuilder getMethodBodyBuilder() {
private MethodBodyBuilder getMethodBodyBuilder() {
if (configProperties.testMode == TestMode.MOCKMVC && configProperties.targetFramework == TestFramework.JUNIT){
return new MockMvcJUnitMethodBodyBuilder(stubContent)
}
if (configProperties.testMode == TestMode.JAXRSCLIENT) {
if (configProperties.targetFramework == TestFramework.JUNIT){
return new JaxRsClientJUnitMethodBodyBuilder(stubContent)
}
return new JaxRsClientSpockMethodBodyBuilder(stubContent)
}
return new MockMvcSpockMethodBodyBuilder(stubContent)

View File

@@ -0,0 +1,39 @@
package io.codearte.accurest.builder
import io.codearte.accurest.dsl.GroovyDsl
import io.codearte.accurest.dsl.internal.Header
import java.util.regex.Pattern
/**
* @author Olga Maciaszek-Sharma
* @since 2016-02-17
*/
class MockMvcJUnitMethodBodyBuilder extends JUnitMethodBodyBuilder {
MockMvcJUnitMethodBodyBuilder(GroovyDsl stubDefinition) {
super(stubDefinition)
}
@Override
protected void validateResponseCodeBlock(BlockBuilder bb) {
bb.addLine("assertThat(response.statusCode()).isEqualTo($response.status.serverValue);")
}
@Override
protected void validateResponseHeadersBlock(BlockBuilder bb) {
response.headers?.collect { Header header ->
bb.addLine("assertThat(response.header(\"$header.name\")).${createHeaderComparison(header.serverValue)}")
}
}
private String createHeaderComparison(Object headerValue) {
String escapedHeader = convertUnicodeEscapesIfRequired("$headerValue")
return "isEqualTo(\"$escapedHeader\");"
}
private String createHeaderComparison(Pattern headerValue) {
String escapedHeader = convertUnicodeEscapesIfRequired("$headerValue")
return "matches(\"$escapedHeader\");"
}
}

View File

@@ -2,13 +2,8 @@ package io.codearte.accurest.builder
import groovy.transform.PackageScope
import groovy.transform.TypeChecked
import groovy.transform.TypeCheckingMode
import io.codearte.accurest.dsl.GroovyDsl
import io.codearte.accurest.dsl.internal.Header
import io.codearte.accurest.dsl.internal.QueryParameter
import io.codearte.accurest.dsl.internal.Request
import io.codearte.accurest.dsl.internal.Url
import io.codearte.accurest.util.MapConverter
import java.util.regex.Pattern
@@ -20,36 +15,12 @@ class MockMvcSpockMethodBodyBuilder extends SpockMethodBodyBuilder {
super(stubDefinition)
}
protected void given(BlockBuilder bb) {
bb.addLine('def request = given()')
bb.indent()
request.headers?.collect { Header header ->
bb.addLine(".header('${getTestSideValue(header.name)}', '${getTestSideValue(header.serverValue)}')")
}
if (request.body) {
bb.addLine(".body('''$bodyAsString''')")
}
if (request.multipart) {
multipartParameters?.each { Map.Entry<String, Object> entry -> bb.addLine(getMultipartParameterLine(entry)) }
}
bb.unindent()
}
protected void when(BlockBuilder bb) {
bb.addLine('def response = given().spec(request)')
bb.indent()
String url = buildUrl(request)
String method = request.method.serverValue.toString().toLowerCase()
bb.addLine(/.${method}("$url")/)
bb.unindent()
}
@Override
protected void validateResponseCodeBlock(BlockBuilder bb) {
bb.addLine("response.statusCode == $response.status.serverValue")
}
@Override
protected void validateResponseHeadersBlock(BlockBuilder bb) {
response.headers?.collect { Header header ->
bb.addLine("response.header('$header.name') ${convertHeaderComparison(header.serverValue)}")
@@ -68,30 +39,4 @@ class MockMvcSpockMethodBodyBuilder extends SpockMethodBodyBuilder {
protected String getResponseAsString() {
return 'response.body.asString()'
}
protected String buildUrl(Request request) {
if (request.url)
return getTestSideValue(buildUrlFromUrlPath(request.url))
if (request.urlPath)
return getTestSideValue(buildUrlFromUrlPath(request.urlPath))
throw new IllegalStateException("URL is not set!")
}
@TypeChecked(TypeCheckingMode.SKIP)
protected String buildUrlFromUrlPath(Url url) {
if (hasQueryParams(url)) {
String params = url.queryParameters.parameters
.findAll(this.&allowedQueryParameter)
.inject([] as List<String>) { List<String> result, QueryParameter param ->
result << "${param.name}=${resolveParamValue(param).toString()}"
}
.join('&')
return "${MapConverter.getTestSideValues(url.serverValue)}?$params"
}
return MapConverter.getTestSideValues(url.serverValue)
}
private boolean hasQueryParams(Url url) {
return url.queryParameters
}
}

View File

@@ -1,223 +1,100 @@
package io.codearte.accurest.builder
import groovy.json.JsonOutput
import groovy.json.StringEscapeUtils
import groovy.transform.PackageScope
import groovy.transform.TypeChecked
import io.codearte.accurest.dsl.GroovyDsl
import io.codearte.accurest.dsl.internal.*
import io.codearte.accurest.util.ContentType
import io.codearte.accurest.util.MapConverter
import io.codearte.accurest.util.JsonToJsonPathsConverter
import io.codearte.accurest.util.JsonPaths
import io.codearte.accurest.dsl.internal.ExecutionProperty
import io.codearte.accurest.dsl.internal.Header
import io.codearte.accurest.dsl.internal.NamedProperty
import io.codearte.accurest.dsl.internal.Request
import static io.codearte.accurest.util.ContentUtils.getGroovyMultipartFileParameterContent
import static io.codearte.accurest.util.ContentUtils.*
/**
* @author Jakub Kubrynski
*/
@PackageScope
@TypeChecked
abstract class SpockMethodBodyBuilder {
protected final Request request
protected final Response response
abstract class SpockMethodBodyBuilder extends MethodBodyBuilder {
SpockMethodBodyBuilder(GroovyDsl stubDefinition) {
this.request = stubDefinition.request
this.response = stubDefinition.response
super(stubDefinition)
}
void appendTo(BlockBuilder blockBuilder) {
blockBuilder.startBlock()
givenBlock(blockBuilder)
whenBlock(blockBuilder)
thenBlock(blockBuilder)
blockBuilder.endBlock()
}
protected void thenBlock(BlockBuilder bb) {
bb.addLine('then:')
bb.startBlock()
then(bb)
bb.endBlock()
}
protected void whenBlock(BlockBuilder bb) {
bb.addLine('when:')
bb.startBlock()
when(bb)
bb.endBlock().addEmptyLine()
}
protected void givenBlock(BlockBuilder bb) {
bb.addLine('given:')
bb.startBlock()
given(bb)
bb.endBlock().addEmptyLine()
}
protected void given(BlockBuilder bb) {}
protected abstract void when(BlockBuilder bb)
protected abstract void validateResponseCodeBlock(BlockBuilder bb)
protected abstract void validateResponseHeadersBlock(BlockBuilder bb)
protected abstract String getResponseAsString()
protected void then(BlockBuilder bb) {
validateResponseCodeBlock(bb)
if (response.headers) {
validateResponseHeadersBlock(bb)
}
if (response.body) {
bb.endBlock()
bb.addLine('and:').startBlock()
validateResponseBodyBlock(bb)
}
}
protected void validateResponseBodyBlock(BlockBuilder bb) {
def responseBody = response.body.serverValue
ContentType contentType = getResponseContentType()
if (responseBody instanceof GString) {
responseBody = extractValue(responseBody, contentType, { DslProperty dslProperty -> dslProperty.serverValue })
}
if (contentType == ContentType.JSON) {
appendJsonPath(bb, responseAsString)
JsonPaths jsonPaths = JsonToJsonPathsConverter.transformToJsonPathWithTestsSideValues(responseBody)
jsonPaths.each {
bb.addLine("assertThat(parsedJson)" + it.method())
}
processBodyElement(bb, "", responseBody)
} else if (contentType == ContentType.XML) {
bb.addLine("def responseBody = new XmlSlurper().parseText($responseAsString)")
// TODO xml validation
} else {
bb.addLine("def responseBody = ($responseAsString)")
processText(bb, "", responseBody as String)
}
}
protected void processText(BlockBuilder blockBuilder, String property, String value) {
if (value.startsWith('$')) {
value = value.substring(1).replaceAll('\\$value', "responseBody$property")
blockBuilder.addLine(value)
} else {
blockBuilder.addLine("responseBody$property == \"${value}\"")
}
}
protected String
protected String getBodyAsString() {
Object bodyValue = extractServerValueFromBody(request.body.serverValue)
String json = new JsonOutput().toJson(bodyValue)
json = convertUnicodeEscapes(json)
return trimRepeatedQuotes(json)
}
protected Map<String, Object> getMultipartParameters() {
return (Map<String, Object>)request?.multipart?.serverValue
}
protected String getMultipartParameterLine(Map.Entry<String, Object> parameter) {
if (parameter.value instanceof NamedProperty) {
return ".multiPart(${getMultipartFileParameterContent(parameter.key, (NamedProperty) parameter.value)})"
}
return ".param('$parameter.key', '$parameter.value')"
}
protected String convertUnicodeEscapes(String json) {
return StringEscapeUtils.unescapeJavaScript(json)
}
protected String trimRepeatedQuotes(String toTrim) {
return toTrim.startsWith('"') ? toTrim.replaceAll('"', '') : toTrim
}
protected Object extractServerValueFromBody(bodyValue) {
if (bodyValue instanceof GString) {
bodyValue = extractValue(bodyValue, { DslProperty dslProperty -> dslProperty.serverValue })
} else {
bodyValue = MapConverter.transformValues(bodyValue, { it instanceof DslProperty ? it.serverValue : it })
}
return bodyValue
}
protected boolean allowedQueryParameter(QueryParameter param) {
return allowedQueryParameter(param.serverValue)
}
protected boolean allowedQueryParameter(MatchingStrategy matchingStrategy) {
return matchingStrategy.type != MatchingStrategy.Type.ABSENT
}
protected boolean allowedQueryParameter(Object o) {
return true
}
protected String resolveParamValue(QueryParameter param) {
return resolveParamValue(param.serverValue)
}
protected String resolveParamValue(Object value) {
return value.toString()
}
protected String resolveParamValue(MatchingStrategy matchingStrategy) {
return matchingStrategy.serverValue.toString()
}
protected void processBodyElement(BlockBuilder blockBuilder, String property, Object value) {
}
protected void appendJsonPath(BlockBuilder blockBuilder, String json) {
blockBuilder.addLine("DocumentContext parsedJson = JsonPath.parse($json)")
@Override
protected String getResponseBodyPropertyComparisonString(String property, String value) {
return "responseBody$property == \"${value}\""
}
@Override
protected void processBodyElement(BlockBuilder blockBuilder, String property, ExecutionProperty exec) {
blockBuilder.addLine("${exec.insertValue("parsedJson.read('\\\$$property')")}")
}
@Override
protected void processBodyElement(BlockBuilder blockBuilder, String property, Map.Entry entry) {
processBodyElement(blockBuilder, property + "." + entry.key, entry.value)
}
protected void processBodyElement(BlockBuilder blockBuilder, String property, Map map) {
map.each {
processBodyElement(blockBuilder, property, it)
}
@Override
protected String addCommentSignIfRequired(String baseString) {
return baseString
}
protected void processBodyElement(BlockBuilder blockBuilder, String property, List list) {
list.eachWithIndex { listElement, listIndex ->
String prop = "$property[$listIndex]" ?: ''
processBodyElement(blockBuilder, prop, listElement)
}
@Override
protected BlockBuilder addColonIfRequired(BlockBuilder blockBuilder) {
return blockBuilder
}
protected ContentType getRequestContentType() {
ContentType contentType = recognizeContentTypeFromHeader(request.headers)
if (contentType == ContentType.UNKNOWN) {
contentType = recognizeContentTypeFromContent(request.body.serverValue)
}
return contentType
@Override
protected String getPropertyInListString(String property, Integer listIndex) {
"$property[$listIndex]" ?: ''
}
protected ContentType getResponseContentType() {
ContentType contentType = recognizeContentTypeFromHeader(response.headers)
if (contentType == ContentType.UNKNOWN) {
contentType = recognizeContentTypeFromContent(response.body.serverValue)
}
return contentType
@Override
protected String convertUnicodeEscapesIfRequired(String json) {
return StringEscapeUtils.unescapeJavaScript(json)
}
protected String getTestSideValue(Object object) {
return MapConverter.getTestSideValues(object).toString()
@Override
protected String getParsedXmlResponseBodyString(String responseString) {
return "def responseBody = new XmlSlurper().parseText($responseString)"
}
@Override
protected String getSimpleResponseBodyString(String responseString) {
return "def responseBody = ($responseString)"
}
@Override
protected String getResponseString(Request request) {
return 'def response = given().spec(request)'
}
@Override
protected String getRequestString() {
return 'def request = given()'
}
@Override
protected String getHeaderString(Header header) {
return ".header('${getTestSideValue(header.name)}', '${getTestSideValue(header.serverValue)}')"
}
@Override
protected String getBodyString(String bodyAsString) {
return ".body('''$bodyAsString''')"
}
@Override
protected String getMultipartFileParameterContent(String propertyName, NamedProperty propertyValue) {
return getGroovyMultipartFileParameterContent(propertyName, propertyValue)
}
@Override
protected String getParameterString(Map.Entry<String, Object> parameter) {
return ".param('$parameter.key', '$parameter.value')"
}
}

View File

@@ -4,8 +4,8 @@ package io.codearte.accurest.config
* @author Jakub Kubrynski
*/
enum TestFramework {
JUNIT("public ", "public void ", ";", ".java", "Test", "org.junit.Ignore", "org.junit.FixMethodOrder", "@FixMethodOrder(MethodSorters.NAME_ASCENDING)"),
SPOCK("", "def ", "", ".groovy", "Spec", "spock.lang.Ignore", "spock.lang.Stepwise", "@Stepwise")
JUNIT("public ", "public void ", ";", ".java", "Test", "org.junit.Ignore", ["org.junit.FixMethodOrder", "org.junit.runners.MethodSorters"], "@FixMethodOrder(MethodSorters.NAME_ASCENDING)"),
SPOCK("", "def ", "", ".groovy", "Spec", "spock.lang.Ignore", ["spock.lang.Stepwise"], "@Stepwise")
private final String classModifier
private final String methodModifier
@@ -13,18 +13,18 @@ enum TestFramework {
private final String classExtension;
private final String classNameSuffix;
private final String ignoreClass
private final String orderAnnotationImport
private final List<String> orderAnnotationImports
private final String orderAnnotation
TestFramework(String classModifier, String methodModifier, String lineSuffix, String classExtension, String classNameSuffix,
String ignoreClass, String orderAnnotationImport, String orderAnnotation) {
String ignoreClass, List<String> orderAnnotationImports, String orderAnnotation) {
this.classModifier = classModifier
this.lineSuffix = lineSuffix
this.methodModifier = methodModifier
this.classExtension = classExtension
this.classNameSuffix = classNameSuffix
this.ignoreClass = ignoreClass
this.orderAnnotationImport = orderAnnotationImport
this.orderAnnotationImports = orderAnnotationImports
this.orderAnnotation = orderAnnotation
}
@@ -52,8 +52,8 @@ enum TestFramework {
return ignoreClass
}
String getOrderAnnotationImport() {
return orderAnnotationImport
List<String> getOrderAnnotationImport() {
return orderAnnotationImports
}
String getOrderAnnotation() {

View File

@@ -1,10 +1,10 @@
package io.codearte.accurest.dsl.internal;
package io.codearte.accurest.dsl.internal
import groovy.transform.CompileStatic;
import groovy.transform.EqualsAndHashCode;
import groovy.transform.CompileStatic
import groovy.transform.EqualsAndHashCode
import groovy.transform.ToString
import static io.codearte.accurest.util.ValidateUtils.validateServerValueIsAvailable;
import static io.codearte.accurest.util.ValidateUtils.validateServerValueIsAvailable
@EqualsAndHashCode(includeFields = true)
@ToString(includePackage = false, includeFields = true, ignoreNulls = true, includeNames = true)

View File

@@ -1,8 +1,8 @@
package io.codearte.accurest.dsl.internal
import groovy.transform.CompileStatic;
import groovy.transform.CompileStatic
import groovy.transform.EqualsAndHashCode
import groovy.transform.ToString;
import groovy.transform.ToString
@ToString(includePackage = false, includeFields = true, includeNames = true)
@EqualsAndHashCode(includeFields = true)

View File

@@ -2,7 +2,6 @@ package io.codearte.accurest.file
import com.google.common.collect.ArrayListMultimap
import com.google.common.collect.ListMultimap
import com.google.common.collect.Multimap
import org.apache.commons.io.FilenameUtils
import java.nio.file.FileSystem

View File

@@ -15,6 +15,7 @@ import org.codehaus.groovy.runtime.GStringImpl
import java.util.regex.Matcher
import java.util.regex.Pattern
import static org.apache.commons.lang3.StringEscapeUtils.escapeJava
import static org.apache.commons.lang3.StringEscapeUtils.escapeJson
import static org.apache.commons.lang3.StringEscapeUtils.escapeXml11
@@ -321,8 +322,13 @@ class ContentUtils {
return ContentType.UNKNOWN
}
static String getMultipartFileParameterContent(String propertyName, NamedProperty propertyValue) {
static String getGroovyMultipartFileParameterContent(String propertyName, NamedProperty propertyValue) {
return "'$propertyName', '$propertyValue.name.serverValue', '$propertyValue.value.serverValue'.bytes"
}
static String getJavaMultipartFileParameterContent(String propertyName, NamedProperty propertyValue) {
return """"${escapeJava(propertyName)}", "${escapeJava(propertyValue.name.serverValue as String)}", "${escapeJava(propertyValue.value.serverValue as String)}".getBytes()"""
}
}

View File

@@ -2,6 +2,8 @@ package io.codearte.accurest.util;
import com.blogspot.toomuchcoding.jsonassert.JsonVerifiable;
import static org.apache.commons.lang3.StringEscapeUtils.escapeJava;
/**
* @author Marcin Grzejszczak
*/
@@ -11,7 +13,7 @@ class DelegatingJsonVerifiable implements MethodBufferingJsonVerifiable {
private final StringBuffer methodsBuffer;
DelegatingJsonVerifiable(JsonVerifiable delegate,
StringBuffer methodsBuffer) {
StringBuffer methodsBuffer) {
this.delegate = delegate;
this.methodsBuffer = new StringBuffer(methodsBuffer.toString());
}
@@ -100,7 +102,7 @@ class DelegatingJsonVerifiable implements MethodBufferingJsonVerifiable {
if (delegate.isAssertingAValueInArray()) {
readyToCheck.methodsBuffer.append(".value()");
} else {
readyToCheck.appendMethodWithQuotedValue("isEqualTo", value);
readyToCheck.appendMethodWithQuotedValue("isEqualTo", escapeJava(value));
}
return readyToCheck;
}
@@ -137,7 +139,7 @@ class DelegatingJsonVerifiable implements MethodBufferingJsonVerifiable {
if (delegate.isAssertingAValueInArray()) {
readyToCheck.methodsBuffer.append(".value()");
} else {
readyToCheck.appendMethodWithQuotedValue("matches", value);
readyToCheck.appendMethodWithQuotedValue("matches", escapeJava(value));
}
return readyToCheck;
}

View File

@@ -0,0 +1,92 @@
package io.codearte.accurest
import io.codearte.accurest.config.AccurestConfigProperties
import io.codearte.accurest.config.TestMode
import io.codearte.accurest.file.Contract
import org.junit.Rule
import org.junit.rules.TemporaryFolder
import spock.lang.Specification
import spock.lang.Unroll
import static io.codearte.accurest.config.TestFramework.JUNIT
import static io.codearte.accurest.config.TestFramework.SPOCK
class SingleTestGeneratorSpec extends Specification {
@Rule
TemporaryFolder tmpFolder = new TemporaryFolder()
File file
static List<String> jUnitClassStrings = ['package test;', 'import com.jayway.jsonpath.DocumentContext;', 'import com.jayway.jsonpath.JsonPath;',
'import org.junit.FixMethodOrder;', 'import org.junit.Ignore;', 'import org.junit.Test;', 'import org.junit.runners.MethodSorters;',
'import static com.blogspot.toomuchcoding.jsonassert.JsonAssertion.assertThatJson;', 'import static com.jayway.restassured.module.mockmvc.RestAssuredMockMvc.*;',
'@FixMethodOrder(MethodSorters.NAME_ASCENDING)', '@Test', '@Ignore', 'mport com.jayway.restassured.module.mockmvc.specification.MockMvcRequestSpecification;',
'import com.jayway.restassured.response.ResponseOptions;', 'import static org.assertj.core.api.Assertions.assertThat;']
static List<String> spockClassStrings = ['package test', 'import com.jayway.jsonpath.DocumentContext', 'import com.jayway.jsonpath.JsonPath',
'import spock.lang.Ignore', 'import spock.lang.Specification', 'import spock.lang.Stepwise',
'import static com.blogspot.toomuchcoding.jsonassert.JsonAssertion.assertThatJson', 'import static com.jayway.restassured.module.mockmvc.RestAssuredMockMvc.*',
'@Stepwise', '@Ignore']
def setup() {
file = tmpFolder.newFile()
file.write("""
io.codearte.accurest.dsl.GroovyDsl.make {
request {
method 'PUT'
url 'url'
}
response {
status 200
}
}
""")
}
@Unroll
def "should build MockMvc test class for #testFramework"() {
given:
AccurestConfigProperties properties = new AccurestConfigProperties();
properties.targetFramework = testFramework
Contract contract = new Contract(file.toPath(), true, 1, 2)
contract.ignored >> true
contract.order >> 2
SingleTestGenerator testGenerator = new SingleTestGenerator(properties)
when:
String clazz = testGenerator.buildClass([contract], "test", "test")
then:
classStrings.each { clazz.contains(it) }
where:
testFramework | classStrings
JUNIT | jUnitClassStrings
SPOCK | spockClassStrings
}
@Unroll
def "should build JaxRs test class for #testFramework"() {
given:
AccurestConfigProperties properties = new AccurestConfigProperties();
properties.testMode = TestMode.JAXRSCLIENT
properties.targetFramework = testFramework
Contract contract = new Contract(file.toPath(), true, 1, 2)
contract.ignored >> true
contract.order >> 2
SingleTestGenerator testGenerator = new SingleTestGenerator(properties)
when:
String clazz = testGenerator.buildClass([contract], "test", "test")
then:
classStrings.each { clazz.contains(it) }
where:
testFramework | classStrings
JUNIT | ['import static javax.ws.rs.client.Entity.*;', 'import javax.ws.rs.core.Response;']
SPOCK | ['import static javax.ws.rs.client.Entity.*;']
}
}

View File

@@ -0,0 +1,612 @@
package io.codearte.accurest.builder
import io.codearte.accurest.dsl.GroovyDsl
import io.codearte.accurest.dsl.WireMockStubStrategy
import io.codearte.accurest.dsl.WireMockStubVerifier
import io.codearte.accurest.file.Contract
import spock.lang.Issue
import spock.lang.Specification
import spock.lang.Unroll
class JaxRsClientMethodBuilderSpec extends Specification implements WireMockStubVerifier {
@Unroll
def "should generate assertions for simple response body with #methodBuilderName"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body """{
"property1": "a",
"property2": "b"
}"""
}
}
MethodBodyBuilder builder = methodBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThatJson(parsedJson).field("property1").isEqualTo("a")""")
blockBuilder.toString().contains("""assertThatJson(parsedJson).field("property2").isEqualTo("b")""")
and:
stubMappingIsValidWireMockStub(contractDsl)
where:
methodBuilderName | methodBuilder
"JaxRsClientSpockMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientSpockMethodBodyBuilder(dsl) }
"JaxRsClientJUnitMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientJUnitMethodBodyBuilder(dsl) }
}
@Issue("#187")
@Unroll
def "should generate assertions for null and boolean values with #methodBuilderName"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body """{
"property1": "true",
"property2": null,
"property3": false
}"""
}
}
MethodBodyBuilder builder = methodBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThatJson(parsedJson).field("property3").isEqualTo(false)""")
blockBuilder.toString().contains("""assertThatJson(parsedJson).field("property2").isNull()""")
blockBuilder.toString().contains("""assertThatJson(parsedJson).field("property1").isEqualTo("true")""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
where:
methodBuilderName | methodBuilder
"JaxRsClientSpockMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientSpockMethodBodyBuilder(dsl) }
"JaxRsClientJUnitMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientJUnitMethodBodyBuilder(dsl) }
}
@Issue("#79")
@Unroll
def "should generate assertions for simple response body constructed from map with a list with #methodBuilderName"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body(
property1: 'a',
property2: [
[a: 'sth'],
[b: 'sthElse']
]
)
}
}
MethodBodyBuilder builder = methodBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThatJson(parsedJson).field("property1").isEqualTo("a")""")
blockBuilder.toString().contains("""assertThatJson(parsedJson).array("property2").contains("a").isEqualTo("sth")""")
blockBuilder.toString().contains("""assertThatJson(parsedJson).array("property2").contains("b").isEqualTo("sthElse")""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
where:
methodBuilderName | methodBuilder
"JaxRsClientSpockMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientSpockMethodBodyBuilder(dsl) }
"JaxRsClientJUnitMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientJUnitMethodBodyBuilder(dsl) }
}
@Issue("#82")
@Unroll
def "should generate proper request when body constructed from map with a list with #methodBuilderName"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
body(
items: ['HOP']
)
}
response {
status 200
}
}
MethodBodyBuilder builder = methodBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains(bodyString)
and:
stubMappingIsValidWireMockStub(contractDsl)
where:
methodBuilderName | methodBuilder | bodyString
"JaxRsClientSpockMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientSpockMethodBodyBuilder(dsl) } | """entity('{\"items\":[\"HOP\"]}', 'application/json')"""
"JaxRsClientJUnitMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientJUnitMethodBodyBuilder(dsl) } | 'entity("{\\"items\\":[\\"HOP\\"]}", "application/json")'
}
@Issue("#88")
@Unroll
def "should generate proper request when body constructed from GString with #methodBuilderName"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
body(
"property1=VAL1"
)
}
response {
status 200
}
}
MethodBodyBuilder builder = methodBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains(bodyString)
and:
stubMappingIsValidWireMockStub(contractDsl)
where:
methodBuilderName | methodBuilder | bodyString
"JaxRsClientSpockMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientSpockMethodBodyBuilder(dsl) } | """entity('property1=VAL1', 'application/octet-stream')"""
"JaxRsClientJUnitMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientJUnitMethodBodyBuilder(dsl) } | 'entity("\\"property1=VAL1\\"", "application/octet-stream")'
}
@Unroll
def "should generate assertions for array in response body with #methodBuilderName"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body """[
{
"property1": "a"
},
{
"property2": "b"
}]"""
}
}
MethodBodyBuilder builder = methodBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThatJson(parsedJson).array().contains("property1").isEqualTo("a")""")
blockBuilder.toString().contains("""assertThatJson(parsedJson).array().contains("property2").isEqualTo("b")""")
and:
stubMappingIsValidWireMockStub(contractDsl)
where:
methodBuilderName | methodBuilder
"JaxRsClientSpockMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientSpockMethodBodyBuilder(dsl) }
"JaxRsClientJUnitMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientJUnitMethodBodyBuilder(dsl) }
}
@Unroll
def "should generate assertions for array inside response body element with #methodBuilderName"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body """{
"property1": [
{ "property2": "test1"},
{ "property3": "test2"}
]
}"""
}
}
MethodBodyBuilder builder = methodBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThatJson(parsedJson).array("property1").contains("property2").isEqualTo("test1")""")
blockBuilder.toString().contains("""assertThatJson(parsedJson).array("property1").contains("property3").isEqualTo("test2")""")
and:
stubMappingIsValidWireMockStub(contractDsl)
where:
methodBuilderName | methodBuilder
"JaxRsClientSpockMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientSpockMethodBodyBuilder(dsl) }
"JaxRsClientJUnitMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientJUnitMethodBodyBuilder(dsl) }
}
@Unroll
def "should generate assertions for nested objects in response body with #methodBuilderName"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body '''\
{
"property1": "a",
"property2": {"property3": "b"}
}
'''
}
}
MethodBodyBuilder builder = methodBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThatJson(parsedJson).field("property2").field("property3").isEqualTo("b")""")
blockBuilder.toString().contains("""assertThatJson(parsedJson).field("property1").isEqualTo("a")""")
and:
stubMappingIsValidWireMockStub(contractDsl)
where:
methodBuilderName | methodBuilder
"JaxRsClientSpockMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientSpockMethodBodyBuilder(dsl) }
"JaxRsClientJUnitMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientJUnitMethodBodyBuilder(dsl) }
}
@Unroll
def "should generate regex assertions for map objects in response body with #methodBodyName"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body(
property1: "a",
property2: value(
client('123'),
server(regex('[0-9]{3}'))
)
)
headers {
header('Content-Type': 'application/json')
}
}
}
MethodBodyBuilder builder = methodBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThatJson(parsedJson).field("property2").matches("[0-9]{3}")""")
blockBuilder.toString().contains("""assertThatJson(parsedJson).field("property1").isEqualTo("a")""")
and:
stubMappingIsValidWireMockStub(contractDsl)
where:
methodBuilderName | methodBuilder
"JaxRsClientSpockMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientSpockMethodBodyBuilder(dsl) }
"JaxRsClientJUnitMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientJUnitMethodBodyBuilder(dsl) }
}
@Unroll
def "should generate regex assertions for string objects in response body with #methodBuilderName"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body("""{"property1":"a","property2":"${value(client('123'), server(regex('[0-9]{3}')))}"}""")
headers {
header('Content-Type': 'application/json')
}
}
}
MethodBodyBuilder builder = methodBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThatJson(parsedJson).field("property2").matches("[0-9]{3}")""")
blockBuilder.toString().contains("""assertThatJson(parsedJson).field("property1").isEqualTo("a")""")
and:
stubMappingIsValidWireMockStub(contractDsl)
where:
methodBuilderName | methodBuilder
"JaxRsClientSpockMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientSpockMethodBodyBuilder(dsl) }
"JaxRsClientJUnitMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientJUnitMethodBodyBuilder(dsl) }
}
@Unroll
def "should ignore 'Accept' header and use 'request' method with #methodBuilderName"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
headers {
header("Accept", "text/plain")
}
}
response {
status 200
}
}
MethodBodyBuilder builder = methodBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains(requestString)
and:
stubMappingIsValidWireMockStub(contractDsl)
where:
methodBuilderName | methodBuilder | requestString
"JaxRsClientSpockMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientSpockMethodBodyBuilder(dsl) } | "request('text/plain')"
"JaxRsClientJUnitMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientJUnitMethodBodyBuilder(dsl) } | 'request("text/plain")'
}
@Unroll
def "should ignore 'Content-Type' header and use 'entity' method with #methodBuilderName"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
headers {
header("Content-Type", "text/plain")
header("Timer", "123")
}
body ''
}
response {
status 200
}
}
MethodBodyBuilder builder = methodBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
for (String requestString : requestStrings) {
blockBuilder.toString().contains(requestString)
}
!blockBuilder.toString().contains("""Content Type""")
and:
stubMappingIsValidWireMockStub(contractDsl)
where:
methodBuilderName | methodBuilder | requestStrings
"JaxRsClientSpockMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientSpockMethodBodyBuilder(dsl) } | ["""entity('', 'text/plain')""", """header('Timer', '123')"""]
"JaxRsClientJUnitMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientJUnitMethodBodyBuilder(dsl) } | ['entity("\\"\\"", "text/plain")', 'header("Timer", "123")']
}
@Unroll
def "should generate a call with an url path and query parameters with #methodBuilderName"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method 'GET'
urlPath('/users') {
queryParameters {
parameter 'limit': $(client(equalTo("20")), server(equalTo("10")))
parameter 'offset': $(client(containing("20")), server(equalTo("20")))
parameter 'filter': "email"
parameter 'sort': equalTo("name")
parameter 'search': $(client(notMatching(~/^\/[0-9]{2}$/)), server("55"))
parameter 'age': $(client(notMatching("^\\w*\$")), server("99"))
parameter 'name': $(client(matching("Denis.*")), server("Denis.Stepanov"))
parameter 'email': "bob@email.com"
parameter 'hello': $(client(matching("Denis.*")), server(absent()))
parameter 'hello': absent()
}
}
}
response {
status 200
body """
{
"property1": "a",
"property2": "b"
}
"""
}
}
MethodBodyBuilder builder = methodBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
def test = blockBuilder.toString()
then:
test.contains(modifyStringIfRequired.call("queryParam('limit', '10'"))
test.contains(modifyStringIfRequired.call("queryParam('offset', '20'"))
test.contains(modifyStringIfRequired.call("queryParam('filter', 'email'"))
test.contains(modifyStringIfRequired.call("queryParam('sort', 'name'"))
test.contains(modifyStringIfRequired.call("queryParam('search', '55'"))
test.contains(modifyStringIfRequired.call("queryParam('age', '99'"))
test.contains(modifyStringIfRequired.call("queryParam('name', 'Denis.Stepanov'"))
test.contains(modifyStringIfRequired.call("queryParam('email', 'bob@email.com'"))
test.contains(modifyStringIfRequired.call("""assertThatJson(parsedJson).field("property1").isEqualTo("a")"""))
test.contains(modifyStringIfRequired.call("""assertThatJson(parsedJson).field("property2").isEqualTo("b")"""))
and:
stubMappingIsValidWireMockStub(contractDsl)
where:
methodBuilderName | methodBuilder | modifyStringIfRequired
"JaxRsClientSpockMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientSpockMethodBodyBuilder(dsl) } | { String paramString -> paramString }
"JaxRsClientJUnitMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientJUnitMethodBodyBuilder(dsl) } | { String paramString -> paramString.replace("'", "\"") }
}
@Issue('#169')
@Unroll
def "should generate a call with an url path and query parameters with url containing a pattern with #methodBuilderName"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method 'GET'
url($(stub(regex('/foo/[0-9]+')), test('/foo/123456'))) {
queryParameters {
parameter 'limit': $(client(equalTo("20")), server(equalTo("10")))
parameter 'offset': $(client(containing("20")), server(equalTo("20")))
parameter 'filter': "email"
parameter 'sort': equalTo("name")
parameter 'search': $(client(notMatching(~/^\/[0-9]{2}$/)), server("55"))
parameter 'age': $(client(notMatching("^\\w*\$")), server("99"))
parameter 'name': $(client(matching("Denis.*")), server("Denis.Stepanov"))
parameter 'email': "bob@email.com"
parameter 'hello': $(client(matching("Denis.*")), server(absent()))
parameter 'hello': absent()
}
}
}
response {
status 200
body """
{
"property1": "a",
"property2": "b"
}
"""
}
}
MethodBodyBuilder builder = methodBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
def test = blockBuilder.toString()
then:
test.contains(modifyStringIfRequired.call("queryParam('limit', '10'"))
test.contains(modifyStringIfRequired.call("queryParam('offset', '20'"))
test.contains(modifyStringIfRequired.call("queryParam('filter', 'email'"))
test.contains(modifyStringIfRequired.call("queryParam('sort', 'name'"))
test.contains(modifyStringIfRequired.call("queryParam('search', '55'"))
test.contains(modifyStringIfRequired.call("queryParam('age', '99'"))
test.contains(modifyStringIfRequired.call("queryParam('name', 'Denis.Stepanov'"))
test.contains(modifyStringIfRequired.call("queryParam('email', 'bob@email.com'"))
test.contains(modifyStringIfRequired.call("""assertThatJson(parsedJson).field("property1").isEqualTo("a")"""))
test.contains(modifyStringIfRequired.call("""assertThatJson(parsedJson).field("property2").isEqualTo("b")"""))
and:
stubMappingIsValidWireMockStub(contractDsl)
where:
methodBuilderName | methodBuilder | modifyStringIfRequired
"JaxRsClientSpockMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientSpockMethodBodyBuilder(dsl) } | { String paramString -> paramString }
"JaxRsClientJUnitMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientJUnitMethodBodyBuilder(dsl) } | { String paramString -> paramString.replace("'", "\"") }
}
@Unroll
def "should generate test for empty body with #methodBuilderName"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method('POST')
url("/ws/payments")
body("")
}
response {
status 406
}
}
MethodBodyBuilder builder = methodBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
def test = blockBuilder.toString()
then:
test.contains(bodyString)
and:
stubMappingIsValidWireMockStub(contractDsl)
where:
methodBuilderName | methodBuilder | bodyString
"JaxRsClientSpockMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientSpockMethodBodyBuilder(dsl) } | "entity('', 'application/octet-stream')"
"JaxRsClientJUnitMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientJUnitMethodBodyBuilder(dsl) } | 'entity("\\"\\"", "application/octet-stream"'
}
@Unroll
def "should generate test for String in response body with #methodBodyName"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "POST"
url "test"
}
response {
status 200
body "test"
}
}
MethodBodyBuilder builder = methodBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
def test = blockBuilder.toString()
then:
test.contains(bodyDefinitionString)
test.contains(bodyEvaluationString)
and:
stubMappingIsValidWireMockStub(contractDsl)
where:
methodBuilderName | methodBuilder | bodyDefinitionString | bodyEvaluationString
"JaxRsClientSpockMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientSpockMethodBodyBuilder(dsl) } | "String responseAsString = response.readEntity(String)" | 'responseBody == "test"'
"JaxRsClientJUnitMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientJUnitMethodBodyBuilder(dsl) } | 'Object responseBody = (responseAsString);' | 'assertThat(responseBody).isEqualTo("test");'
}
@Issue('#171')
@Unroll
def "should generate test with uppercase method name with #methodBuilderName"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "get"
url "/v1/some_cool_requests/e86df6f693de4b35ae648464c5b0dc08"
}
response {
status 200
headers {
header('Content-Type': 'application/json;charset=UTF-8')
}
body """
{"id":"789fgh","other_data":1268}
"""
}
}
MethodBodyBuilder builder = methodBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
def test = blockBuilder.toString()
then:
test.contains(methodString)
and:
stubMappingIsValidWireMockStub(contractDsl)
where:
methodBuilderName | methodBuilder | methodString
"JaxRsClientSpockMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientSpockMethodBodyBuilder(dsl) } | ".method('GET')"
"JaxRsClientJUnitMethodBodyBuilder" | { GroovyDsl dsl -> new JaxRsClientJUnitMethodBodyBuilder(dsl) } | 'method("GET")'
}
}

View File

@@ -1,524 +0,0 @@
package io.codearte.accurest.builder
import io.codearte.accurest.dsl.GroovyDsl
import io.codearte.accurest.dsl.WireMockStubStrategy
import io.codearte.accurest.dsl.WireMockStubVerifier
import io.codearte.accurest.file.Contract
import spock.lang.Issue
import spock.lang.Specification
class JaxRsClientSpockMethodBuilderSpec extends Specification implements WireMockStubVerifier {
def "should generate assertions for simple response body"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body """{
"property1": "a",
"property2": "b"
}"""
}
}
JaxRsClientSpockMethodBodyBuilder builder = new JaxRsClientSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThat(parsedJson).field("property1").isEqualTo("a")""")
blockBuilder.toString().contains("""assertThat(parsedJson).field("property2").isEqualTo("b")""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
@Issue("#187")
def "should generate assertions for null and boolean values"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body """{
"property1": "true",
"property2": null,
"property3": false
}"""
}
}
JaxRsClientSpockMethodBodyBuilder builder = new JaxRsClientSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThat(parsedJson).field("property3").isEqualTo(false)""")
blockBuilder.toString().contains("""assertThat(parsedJson).field("property2").isNull()""")
blockBuilder.toString().contains("""assertThat(parsedJson).field("property1").isEqualTo("true")""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
@Issue("#79")
def "should generate assertions for simple response body constructed from map with a list"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body(
property1: 'a',
property2: [
[a: 'sth'],
[b: 'sthElse']
]
)
}
}
JaxRsClientSpockMethodBodyBuilder builder = new JaxRsClientSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThat(parsedJson).field("property1").isEqualTo("a")""")
blockBuilder.toString().contains("""assertThat(parsedJson).array("property2").contains("a").isEqualTo("sth")""")
blockBuilder.toString().contains("""assertThat(parsedJson).array("property2").contains("b").isEqualTo("sthElse")""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
@Issue("#82")
def "should generate proper request when body constructed from map with a list"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
body(
items: ['HOP']
)
}
response {
status 200
}
}
JaxRsClientSpockMethodBodyBuilder builder = new JaxRsClientSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""entity('{\"items\":[\"HOP\"]}', 'application/json')""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
@Issue("#88")
def "should generate proper request when body constructed from GString"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
body(
"property1=VAL1"
)
}
response {
status 200
}
}
JaxRsClientSpockMethodBodyBuilder builder = new JaxRsClientSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""entity('property1=VAL1', 'application/octet-stream')""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
def "should generate assertions for array in response body"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body """[
{
"property1": "a"
},
{
"property2": "b"
}]"""
}
}
JaxRsClientSpockMethodBodyBuilder builder = new JaxRsClientSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThat(parsedJson).array().contains("property1").isEqualTo("a")""")
blockBuilder.toString().contains("""assertThat(parsedJson).array().contains("property2").isEqualTo("b")""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
def "should generate assertions for array inside response body element"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body """{
"property1": [
{ "property2": "test1"},
{ "property3": "test2"}
]
}"""
}
}
JaxRsClientSpockMethodBodyBuilder builder = new JaxRsClientSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThat(parsedJson).array("property1").contains("property2").isEqualTo("test1")""")
blockBuilder.toString().contains("""assertThat(parsedJson).array("property1").contains("property3").isEqualTo("test2")""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
def "should generate assertions for nested objects in response body"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body '''\
{
"property1": "a",
"property2": {"property3": "b"}
}
'''
}
}
JaxRsClientSpockMethodBodyBuilder builder = new JaxRsClientSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThat(parsedJson).field("property2").field("property3").isEqualTo("b")""")
blockBuilder.toString().contains("""assertThat(parsedJson).field("property1").isEqualTo("a")""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
def "should generate regex assertions for map objects in response body"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body(
property1: "a",
property2: value(
client('123'),
server(regex('[0-9]{3}'))
)
)
headers {
header('Content-Type': 'application/json')
}
}
}
JaxRsClientSpockMethodBodyBuilder builder = new JaxRsClientSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThat(parsedJson).field("property2").matches("[0-9]{3}")""")
blockBuilder.toString().contains("""assertThat(parsedJson).field("property1").isEqualTo("a")""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
def "should generate regex assertions for string objects in response body"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body("""{"property1":"a","property2":"${value(client('123'), server(regex('[0-9]{3}')))}"}""")
headers {
header('Content-Type': 'application/json')
}
}
}
JaxRsClientSpockMethodBodyBuilder builder = new JaxRsClientSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThat(parsedJson).field("property2").matches("[0-9]{3}")""")
blockBuilder.toString().contains("""assertThat(parsedJson).field("property1").isEqualTo("a")""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
def "should ignore 'Accept' header and use 'request' method"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
headers {
header("Accept", "text/plain")
}
}
response {
status 200
}
}
JaxRsClientSpockMethodBodyBuilder builder = new JaxRsClientSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("request('text/plain')")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
def "should ignore 'Content-Type' header and use 'entity' method"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
headers {
header("Content-Type", "text/plain")
header("Timer", "123")
}
body ''
}
response {
status 200
}
}
JaxRsClientSpockMethodBodyBuilder builder = new JaxRsClientSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""entity('', 'text/plain')""")
blockBuilder.toString().contains("""header('Timer', '123')""")
!blockBuilder.toString().contains("""header('Content-Type'""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
def "should generate a call with an url path and query parameters"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method 'GET'
urlPath('/users') {
queryParameters {
parameter 'limit': $(client(equalTo("20")), server(equalTo("10")))
parameter 'offset': $(client(containing("20")), server(equalTo("20")))
parameter 'filter': "email"
parameter 'sort': equalTo("name")
parameter 'search': $(client(notMatching(~/^\/[0-9]{2}$/)), server("55"))
parameter 'age': $(client(notMatching("^\\w*\$")), server("99"))
parameter 'name': $(client(matching("Denis.*")), server("Denis.Stepanov"))
parameter 'email': "bob@email.com"
parameter 'hello': $(client(matching("Denis.*")), server(absent()))
parameter 'hello': absent()
}
}
}
response {
status 200
body """
{
"property1": "a",
"property2": "b"
}
"""
}
}
JaxRsClientSpockMethodBodyBuilder builder = new JaxRsClientSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
def spockTest = blockBuilder.toString()
then:
spockTest.contains("queryParam('limit', '10'")
spockTest.contains("queryParam('offset', '20'")
spockTest.contains("queryParam('filter', 'email'")
spockTest.contains("queryParam('sort', 'name'")
spockTest.contains("queryParam('search', '55'")
spockTest.contains("queryParam('age', '99'")
spockTest.contains("queryParam('name', 'Denis.Stepanov'")
spockTest.contains("queryParam('email', 'bob@email.com'")
spockTest.contains("""assertThat(parsedJson).field("property1").isEqualTo("a")""")
spockTest.contains("""assertThat(parsedJson).field("property2").isEqualTo("b")""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
@Issue('#169')
def "should generate a call with an url path and query parameters with url containing a pattern"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method 'GET'
url($(stub(regex('/foo/[0-9]+')), test('/foo/123456'))){
queryParameters {
parameter 'limit': $(client(equalTo("20")), server(equalTo("10")))
parameter 'offset': $(client(containing("20")), server(equalTo("20")))
parameter 'filter': "email"
parameter 'sort': equalTo("name")
parameter 'search': $(client(notMatching(~/^\/[0-9]{2}$/)), server("55"))
parameter 'age': $(client(notMatching("^\\w*\$")), server("99"))
parameter 'name': $(client(matching("Denis.*")), server("Denis.Stepanov"))
parameter 'email': "bob@email.com"
parameter 'hello': $(client(matching("Denis.*")), server(absent()))
parameter 'hello': absent()
}
}
}
response {
status 200
body """
{
"property1": "a",
"property2": "b"
}
"""
}
}
JaxRsClientSpockMethodBodyBuilder builder = new JaxRsClientSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
def spockTest = blockBuilder.toString()
then:
spockTest.contains("queryParam('limit', '10'")
spockTest.contains("queryParam('offset', '20'")
spockTest.contains("queryParam('filter', 'email'")
spockTest.contains("queryParam('sort', 'name'")
spockTest.contains("queryParam('search', '55'")
spockTest.contains("queryParam('age', '99'")
spockTest.contains("queryParam('name', 'Denis.Stepanov'")
spockTest.contains("queryParam('email', 'bob@email.com'")
spockTest.contains("""assertThat(parsedJson).field("property1").isEqualTo("a")""")
spockTest.contains("""assertThat(parsedJson).field("property2").isEqualTo("b")""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
def "should generate test for empty body"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method('POST')
url("/ws/payments")
body("")
}
response {
status 406
}
}
JaxRsClientSpockMethodBodyBuilder builder = new JaxRsClientSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
def spockTest = blockBuilder.toString()
then:
spockTest.contains("entity('', 'application/octet-stream')")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
def "should generate test for String in response body"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "POST"
url "test"
}
response {
status 200
body "test"
}
}
JaxRsClientSpockMethodBodyBuilder builder = new JaxRsClientSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
def spockTest = blockBuilder.toString()
then:
spockTest.contains("String responseAsString = response.readEntity(String)")
spockTest.contains('responseBody == "test"')
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
@Issue('#171')
def "should generate test with uppercase method name"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "get"
url "/v1/some_cool_requests/e86df6f693de4b35ae648464c5b0dc08"
}
response {
status 200
headers {
header('Content-Type': 'application/json;charset=UTF-8')
}
body """
{"id":"789fgh","other_data":1268}
"""
}
}
JaxRsClientSpockMethodBodyBuilder builder = new JaxRsClientSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
def spockTest = blockBuilder.toString()
then:
spockTest.contains(".method('GET')")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
}

View File

@@ -1,960 +0,0 @@
package io.codearte.accurest.builder
import io.codearte.accurest.dsl.GroovyDsl
import io.codearte.accurest.dsl.WireMockStubStrategy
import io.codearte.accurest.dsl.WireMockStubVerifier
import io.codearte.accurest.file.Contract
import spock.lang.Issue
import spock.lang.Specification
import spock.lang.Unroll
import java.util.regex.Pattern
/**
* @author Jakub Kubrynski
*/
class MockMvcSpockMethodBuilderSpec extends Specification implements WireMockStubVerifier {
def "should generate assertions for simple response body"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body """{
"property1": "a",
"property2": "b"
}"""
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThat(parsedJson).field("property1").isEqualTo("a")""")
blockBuilder.toString().contains("""assertThat(parsedJson).field("property2").isEqualTo("b")""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
@Issue("#187")
def "should generate assertions for null and boolean values"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body """{
"property1": "true",
"property2": null,
"property3": false
}"""
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThat(parsedJson).field("property1").isEqualTo("true")""")
blockBuilder.toString().contains("""assertThat(parsedJson).field("property2").isNull()""")
blockBuilder.toString().contains("""assertThat(parsedJson).field("property3").isEqualTo(false)""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
@Issue("#79")
def "should generate assertions for simple response body constructed from map with a list"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body(
property1: 'a',
property2: [
[a: 'sth'],
[b: 'sthElse']
]
)
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThat(parsedJson).field("property1").isEqualTo("a")""")
blockBuilder.toString().contains("""assertThat(parsedJson).array("property2").contains("a").isEqualTo("sth")""")
blockBuilder.toString().contains("""assertThat(parsedJson).array("property2").contains("b").isEqualTo("sthElse")""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
@Issue("#82")
def "should generate proper request when body constructed from map with a list"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
body(
items: ['HOP']
)
}
response {
status 200
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains(""".body('''{\"items\":[\"HOP\"]}''')""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
@Issue("#88")
def "should generate proper request when body constructed from GString"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
body(
"property1=VAL1"
)
}
response {
status 200
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains(""".body('''property1=VAL1''')""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
@Issue("185")
def "should generate assertions for a response body containing map with integers as keys"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body(
property: [
14: 0.0,
7 : 0.0
]
)
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThat(parsedJson).field("property").field(7).isEqualTo(0.0)""")
blockBuilder.toString().contains("""assertThat(parsedJson).field("property").field(14).isEqualTo(0.0)""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
def "should generate assertions for array in response body"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body """[
{
"property1": "a"
},
{
"property2": "b"
}]"""
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThat(parsedJson).array().contains("property2").isEqualTo("b")""")
blockBuilder.toString().contains("""assertThat(parsedJson).array().contains("property1").isEqualTo("a")""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
def "should generate assertions for array inside response body element"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body """{
"property1": [
{ "property2": "test1"},
{ "property3": "test2"}
]
}"""
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThat(parsedJson).array("property1").contains("property2").isEqualTo("test1")""")
blockBuilder.toString().contains("""assertThat(parsedJson).array("property1").contains("property3").isEqualTo("test2")""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
def "should generate assertions for nested objects in response body"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body '''\
{
"property1": "a",
"property2": {"property3": "b"}
}
'''
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThat(parsedJson).field("property2").field("property3").isEqualTo("b")""")
blockBuilder.toString().contains("""assertThat(parsedJson).field("property1").isEqualTo("a")""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
def "should generate regex assertions for map objects in response body"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body(
property1: "a",
property2: value(
client('123'),
server(regex('[0-9]{3}'))
)
)
headers {
header('Content-Type': 'application/json')
}
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThat(parsedJson).field("property2").matches("[0-9]{3}")""")
blockBuilder.toString().contains("""assertThat(parsedJson).field("property1").isEqualTo("a")""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
def "should generate regex assertions for string objects in response body"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body("""{"property1":"a","property2":"${value(client('123'), server(regex('[0-9]{3}')))}"}""")
headers {
header('Content-Type': 'application/json')
}
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThat(parsedJson).field("property2").matches("[0-9]{3}")""")
blockBuilder.toString().contains("""assertThat(parsedJson).field("property1").isEqualTo("a")""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
@Issue(["#126", "#143"])
def "should generate escaped regex assertions for string objects in response body"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "GET"
url "test"
}
response {
status 200
body("""{"property":" ${value(client('123'), server(regex('\\d+')))}"}""")
headers {
header('Content-Type': 'application/json')
}
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
then:
blockBuilder.toString().contains("""assertThat(parsedJson).field("property").matches("\\d+")""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
def "should generate a call with an url path and query parameters"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method 'GET'
urlPath('/users') {
queryParameters {
parameter 'limit': $(client(equalTo("20")), server(equalTo("10")))
parameter 'offset': $(client(containing("20")), server(equalTo("20")))
parameter 'filter': "email"
parameter 'sort': equalTo("name")
parameter 'search': $(client(notMatching(~/^\/[0-9]{2}$/)), server("55"))
parameter 'age': $(client(notMatching("^\\w*\$")), server("99"))
parameter 'name': $(client(matching("Denis.*")), server("Denis.Stepanov"))
parameter 'email': "bob@email.com"
parameter 'hello': $(client(matching("Denis.*")), server(absent()))
parameter 'hello': absent()
}
}
}
response {
status 200
body """
{
"property1": "a",
"property2": "b"
}
"""
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
def spockTest = blockBuilder.toString()
then:
spockTest.contains('get("/users?limit=10&offset=20&filter=email&sort=name&search=55&age=99&name=Denis.Stepanov&email=bob@email.com")')
spockTest.contains('assertThat(parsedJson).field("property1").isEqualTo("a")')
spockTest.contains('assertThat(parsedJson).field("property2").isEqualTo("b")')
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
@Issue('#169')
def "should generate a call with an url path and query parameters with url containing a pattern"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method 'GET'
url($(stub(regex('/foo/[0-9]+')), test('/foo/123456'))){
queryParameters {
parameter 'limit': $(client(equalTo("20")), server(equalTo("10")))
parameter 'offset': $(client(containing("20")), server(equalTo("20")))
parameter 'filter': "email"
parameter 'sort': equalTo("name")
parameter 'search': $(client(notMatching(~/^\/[0-9]{2}$/)), server("55"))
parameter 'age': $(client(notMatching("^\\w*\$")), server("99"))
parameter 'name': $(client(matching("Denis.*")), server("Denis.Stepanov"))
parameter 'email': "bob@email.com"
parameter 'hello': $(client(matching("Denis.*")), server(absent()))
parameter 'hello': absent()
}
}
}
response {
status 200
body """
{
"property1": "a",
"property2": "b"
}
"""
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
def spockTest = blockBuilder.toString()
then:
spockTest.contains('get("/foo/123456?limit=10&offset=20&filter=email&sort=name&search=55&age=99&name=Denis.Stepanov&email=bob@email.com")')
spockTest.contains('assertThat(parsedJson).field("property1").isEqualTo("a")')
spockTest.contains('assertThat(parsedJson).field("property2").isEqualTo("b")')
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
def "should generate test for empty body"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method('POST')
url("/ws/payments")
body("")
}
response {
status 406
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
def spockTest = blockBuilder.toString()
then:
spockTest.contains(".body('''''')")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
def "should generate test for String in response body"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "POST"
url "test"
}
response {
status 200
body "test"
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
def spockTest = blockBuilder.toString()
then:
spockTest.contains('def responseBody = (response.body.asString())')
spockTest.contains('responseBody == "test"')
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
@Issue('113')
def "should generate regex test for String in response header"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method 'POST'
url $(client(regex('/partners/[0-9]+/users')), server('/partners/1000/users'))
headers { header 'Content-Type': 'application/json' }
body(
first_name: 'John',
last_name: 'Smith',
personal_id: '12345678901',
phone_number: '500500500',
invitation_token: '00fec7141bb94793bfe7ae1d0f39bda0',
password: 'john'
)
}
response {
status 201
headers {
header 'Location': $(client('http://localhost/partners/1000/users/1001'), server(regex('http://localhost/partners/[0-9]+/users/[0-9]+')))
}
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
def spockTest = blockBuilder.toString()
then:
spockTest.contains('''response.header('Location') ==~ java.util.regex.Pattern.compile('http://localhost/partners/[0-9]+/users/[0-9]+')''')
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
@Issue('115')
def "should generate regex with helper method"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method 'POST'
url $(client(regex('/partners/[0-9]+/users')), server('/partners/1000/users'))
headers { header 'Content-Type': 'application/json' }
body(
first_name: 'John',
last_name: 'Smith',
personal_id: '12345678901',
phone_number: '500500500',
invitation_token: '00fec7141bb94793bfe7ae1d0f39bda0',
password: 'john'
)
}
response {
status 201
headers {
header 'Location': $(client('http://localhost/partners/1000/users/1001'), server(regex("^${hostname()}/partners/[0-9]+/users/[0-9]+")))
}
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
def spockTest = blockBuilder.toString()
then:
spockTest.contains('''response.header('Location') ==~ java.util.regex.Pattern.compile('^((http[s]?|ftp):\\/)\\/?([^:\\/\\s]+)(:[0-9]{1,5})?/partners/[0-9]+/users/[0-9]+')''')
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
def "should work with more complex stuff and jsonpaths"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
priority 10
request {
method 'POST'
url '/validation/client'
headers {
header 'Content-Type': 'application/json'
}
body(
bank_account_number: '0014282912345698765432161182',
email: 'foo@bar.com',
phone_number: '100299300',
personal_id: 'ABC123456'
)
}
response {
status 200
body(errors: [
[property: "bank_account_number", message: "incorrect_format"]
])
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
def spockTest = blockBuilder.toString()
then:
spockTest.contains("""assertThat(parsedJson).array("errors").contains("property").isEqualTo("bank_account_number")""")
spockTest.contains("""assertThat(parsedJson).array("errors").contains("message").isEqualTo("incorrect_format")""")
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
def "should work properly with GString url"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method 'PUT'
url "/partners/${value(client(regex('^[0-9]*$')), server('11'))}/agents/11/customers/09665703Z"
headers {
header 'Content-Type': 'application/json'
}
body(
first_name: 'Josef',
)
}
response {
status 422
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
def spockTest = blockBuilder.toString()
then:
spockTest.contains('''/partners/11/agents/11/customers/09665703Z''')
and:
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
def "should resolve properties in GString with regular expression"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
priority 1
request {
method 'POST'
url '/users/password'
headers {
header 'Content-Type': 'application/json'
}
body(
email: $(client(regex(email())), server('not.existing@user.com')),
callback_url: $(client(regex(hostname())), server('http://partners.com'))
)
}
response {
status 404
headers {
header 'Content-Type': 'application/json'
}
body(
code: 4,
message: "User not found by email = [${value(server(regex(email())), client('not.existing@user.com'))}]"
)
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
def spockTest = blockBuilder.toString()
then:
spockTest.contains("""assertThat(parsedJson).field("message").matches("User not found by email = \\\\[[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\\\\.[a-zA-Z]{2,4}\\\\]")""")
}
@Issue('42')
@Unroll
def "should not omit the optional field in the test creation"() {
given:
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
def spockTest = blockBuilder.toString()
then:
spockTest.contains('''"email":"abc@abc.com"''')
spockTest.contains("""assertThat(parsedJson).field("code").matches("(123123)?")""")
!spockTest.contains('''REGEXP''')
!spockTest.contains('''OPTIONAL''')
!spockTest.contains('''OptionalProperty''')
where:
contractDsl << [
GroovyDsl.make {
priority 1
request {
method 'POST'
url '/users/password'
headers {
header 'Content-Type': 'application/json'
}
body(
email: $(stub(optional(regex(email()))), test('abc@abc.com')),
callback_url: $(stub(regex(hostname())), test('http://partners.com'))
)
}
response {
status 404
headers {
header 'Content-Type': 'application/json'
}
body(
code: value(stub("123123"), test(optional("123123"))),
message: "User not found by email = [${value(test(regex(email())), stub('not.existing@user.com'))}]"
)
}
},
GroovyDsl.make {
priority 1
request {
method 'POST'
url '/users/password'
headers {
header 'Content-Type': 'application/json'
}
body(
""" {
"email" : "${value(stub(optional(regex(email()))), test('abc@abc.com'))}",
"callback_url" : "${value(client(regex(hostname())), server('http://partners.com'))}"
}
"""
)
}
response {
status 404
headers {
header 'Content-Type': 'application/json'
}
body(
""" {
"code" : "${value(stub(123123), test(optional(123123)))}",
"message" : "User not found by email = [${value(server(regex(email())), client('not.existing@user.com'))}]"
}
"""
)
}
}
]
}
@Issue('72')
def "should make the execute method work"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method """PUT"""
url """/fraudcheck"""
body("""
{
"clientPesel":"${value(client(regex('[0-9]{10}')), server('1234567890'))}",
"loanAmount":123.123
}
"""
)
headers {
header("""Content-Type""", """application/vnd.fraud.v1+json""")
}
}
response {
status 200
body( """{
"fraudCheckStatus": "OK",
"rejectionReason": ${value(client(null), server(execute('assertThatRejectionReasonIsNull($it)')))}
}""")
headers {
header('Content-Type': 'application/vnd.fraud.v1+json')
}
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
def spockTest = blockBuilder.toString()
then:
spockTest.contains('''assertThatRejectionReasonIsNull(parsedJson.read('$.rejectionReason'))''')
}
def "should support inner map and list definitions"() {
given:
Pattern PHONE_NUMBER = Pattern.compile(/[+\w]*/)
Pattern ANYSTRING = Pattern.compile(/.*/)
Pattern NUMBERS = Pattern.compile(/[\d\.]*/)
Pattern DATETIME = ANYSTRING
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "PUT"
url "/v1/payments/e86df6f693de4b35ae648464c5b0dc09/client_data"
headers {
header('Content-Type': 'application/json')
}
body(
client: [
first_name: $(stub(regex(onlyAlphaUnicode())), test('Denis')),
last_name: $(stub(regex(onlyAlphaUnicode())), test('FakeName')),
email: $(stub(regex(email())), test('fakemail@fakegmail.com')),
fax: $(stub(PHONE_NUMBER), test('+xx001213214')),
phone: $(stub(PHONE_NUMBER), test('2223311')),
data_of_birth: $(stub(DATETIME), test('2002-10-22T00:00:00Z'))
],
client_id_card: [
id: $(stub(ANYSTRING), test('ABC12345')),
date_of_issue: $(stub(ANYSTRING), test('2002-10-02T00:00:00Z')),
address: [
street: $(stub(ANYSTRING), test('Light Street')),
city: $(stub(ANYSTRING), test('Fire')),
region: $(stub(ANYSTRING), test('Skys')),
country: $(stub(ANYSTRING), test('HG')),
zip: $(stub(NUMBERS), test('658965'))
]
],
incomes_and_expenses: [
monthly_income: $(stub(NUMBERS), test('0.0')),
monthly_loan_repayments: $(stub(NUMBERS), test('100')),
monthly_living_expenses: $(stub(NUMBERS), test('22'))
],
additional_info: [
allow_to_contact: $(stub(optional(regex(anyBoolean()))), test('true'))
]
)
}
response {
status 200
headers {
header('Content-Type': 'application/json')
}
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
def spockTest = blockBuilder.toString()
then:
spockTest.contains '"street":"Light Street"'
!spockTest.contains("clientValue")
!spockTest.contains("cursor")
}
def "shouldn't generate unicode escape characters"() {
given:
Pattern ONLY_ALPHA_UNICODE = Pattern.compile(/[\p{L}]*/)
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "PUT"
url "/v1/payments/e86df6f693de4b35ae648464c5b0dc09/енев"
headers {
header('Content-Type': 'application/json')
}
body(
client: [
first_name: $(stub(ONLY_ALPHA_UNICODE), test('Пенева')),
last_name : $(stub(ONLY_ALPHA_UNICODE), test('Пенева'))
]
)
}
response {
status 200
headers {
header('Content-Type': 'application/json')
}
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.appendTo(blockBuilder)
def spockTest = blockBuilder.toString()
then:
!spockTest.contains("\\u041f")
}
@Issue('177')
def "should generate proper test code when having multiline body"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "PUT"
url "/multiline"
body('''hello,
World.''')
}
response {
status 200
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.given(blockBuilder)
def spockTest = blockBuilder.toString()
then:
spockTest.contains("""'''hello,
World.'''""")
}
@Issue('180')
def "should generate proper test code when having multipart parameters"(){
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "PUT"
url "/multipart"
headers {
header('content-type', 'multipart/form-data;boundary=AaB03x')
}
multipart(
formParameter: value(client(regex('.+')), server('"formParameterValue"')),
someBooleanParameter: value(client(regex('(true|false)')), server('true')),
file: named(value(client(regex('.+')), server('filename.csv')), value(client(regex('.+')), server('file content')))
)
}
response {
status 200
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.given(blockBuilder)
def spockTest = blockBuilder.toString()
then:
spockTest.contains("""'content-type', 'multipart/form-data;boundary=AaB03x'""")
spockTest.contains(""".param('formParameter', '"formParameterValue"'""")
spockTest.contains(""".param('someBooleanParameter', 'true')""")
spockTest.contains(""".multiPart('file', 'filename.csv', 'file content'.bytes)""")
}
@Issue('180')
def "should generate proper test code when having multipart parameters with named as map"() {
given:
GroovyDsl contractDsl = GroovyDsl.make {
request {
method "PUT"
url "/multipart"
multipart(
formParameter: value(client(regex('".+"')), server('"formParameterValue"')),
someBooleanParameter: value(client(regex('(true|false)')), server('true')),
file: named(
name: value(client(regex('.+')), server('filename.csv')),
content: value(client(regex('.+')), server('file content')))
)
}
response {
status 200
}
}
MockMvcSpockMethodBodyBuilder builder = new MockMvcSpockMethodBodyBuilder(contractDsl)
BlockBuilder blockBuilder = new BlockBuilder(" ")
when:
builder.given(blockBuilder)
def spockTest = blockBuilder.toString()
then:
spockTest.contains('.multiPart')
}
}

View File

@@ -1,6 +1,7 @@
package io.codearte.accurest.dsl
import com.github.tomakehurst.wiremock.stubbing.StubMapping
import io.codearte.accurest.file.Contract
import java.util.regex.Pattern
@@ -14,4 +15,8 @@ trait WireMockStubVerifier {
assert !mappingDefinition.contains('io.codearte.accurest.dsl.internal')
}
void stubMappingIsValidWireMockStub(GroovyDsl contractDsl) {
stubMappingIsValidWireMockStub(new WireMockStubStrategy("Test", new Contract(null, false, 0, null), contractDsl).toWireMockClientStub())
}
}

View File

@@ -1,7 +1,6 @@
package io.codearte.accurest.file
import com.google.common.collect.ListMultimap
import com.google.common.collect.Multimap
import spock.lang.Specification
import java.nio.file.Path

View File

@@ -483,7 +483,7 @@ class JsonToJsonPathsConverterSpec extends Specification {
JsonPaths pathAndValues = JsonToJsonPathsConverter.transformToJsonPathWithTestsSideValues(json)
then:
pathAndValues.find {
it.method()== """.field("property2").matches("\\d+")""" &&
it.method()== """.field("property2").matches("\\\\d+")""" &&
it.jsonPath() == """\$[?(@.property2 =~ /\\d+/)]"""
}
and:

View File

@@ -30,6 +30,7 @@ class AccurestGradlePlugin implements Plugin<Project> {
deprecatedCreateAndConfigureGenerateWiremockClientStubsFromDslTask()
project.dependencies.add("testCompile", "com.github.tomakehurst:wiremock:2.0.5-beta")
project.dependencies.add("testCompile", "com.blogspot.toomuchcoding:jsonassert:${extension.getJsonAssertVersion()}")
project.dependencies.add("testCompile", "org.assertj:assertj-core:2.3.0")
project.afterEvaluate {
def hasIdea = project.plugins.findPlugin(IDEA_PLUGIN_CLASS)

View File

@@ -0,0 +1,29 @@
package io.codearte.accurest.plugin
import nebula.test.IntegrationSpec
import java.nio.file.Files
import java.nio.file.Path
import static java.nio.charset.StandardCharsets.UTF_8
import static java.nio.charset.StandardCharsets.UTF_8
/**
* @author Olga Maciaszek-Sharma
@since 23.02.16
*/
class AccurestIntegrationSpec extends IntegrationSpec{
public static final String SPOCK = "targetFramework = 'Spock'"
public static final String JUNIT = "targetFramework = 'JUnit'"
public static final String MVC_SPEC = "baseClassForTests = 'com.blogspot.toomuchcoding.MvcSpec'"
public static final String MVC_TEST = "baseClassForTests = 'com.blogspot.toomuchcoding.MvcTest'"
protected void switchToJunitTestFramework() {
Path path = buildFile.toPath()
String content = new StringBuilder(new String(Files.readAllBytes(path), UTF_8)).replaceAll(SPOCK, JUNIT)
.replaceAll(MVC_SPEC, MVC_TEST)
Files.write(path, content.getBytes(UTF_8))
}
}

View File

@@ -1,21 +1,29 @@
package io.codearte.accurest.plugin
import nebula.test.IntegrationSpec
import spock.lang.Stepwise
@Stepwise
class SampleJerseyProjectSpec extends IntegrationSpec {
class SampleJerseyProjectSpec extends AccurestIntegrationSpec {
void setup() {
copyResources("functionalTest/sampleJerseyProject", "")
runTasksSuccessfully('clean') //delete accidental output when previously importing SimpleBoot into Idea to tweak it
runTasksSuccessfully('clean')
//delete accidental output when previously importing SimpleBoot into Idea to tweak it
}
def "should pass basic flow"() {
def "should pass basic flow for Spock"() {
given:
assert fileExists('build.gradle')
expect:
runTasksSuccessfully('check')
}
def "should pass basic flow for JUnit"() {
given:
switchToJunitTestFramework()
assert fileExists('build.gradle')
expect:
runTasksSuccessfully('check')
}
}

View File

@@ -1,21 +1,28 @@
package io.codearte.accurest.plugin
import nebula.test.IntegrationSpec
import spock.lang.Stepwise
@Stepwise
class SampleProjectSpec extends IntegrationSpec {
class SampleProjectSpec extends AccurestIntegrationSpec {
void setup() {
copyResources("functionalTest/sampleProject", "")
runTasksSuccessfully('clean') //delete accidental output when previously importing SimpleBoot into Idea to tweak it
}
def "should pass basic flow"() {
def "should pass basic flow for Spock"() {
given:
assert fileExists('build.gradle')
expect:
runTasksSuccessfully('check')
}
def "should pass basic flow for JUnit"() {
given:
switchToJunitTestFramework()
assert fileExists('build.gradle')
expect:
runTasksSuccessfully('check')
}
}

View File

@@ -4,18 +4,26 @@ import nebula.test.IntegrationSpec
import spock.lang.Stepwise
@Stepwise
class ScenarioProjectSpec extends IntegrationSpec {
class ScenarioProjectSpec extends AccurestIntegrationSpec {
void setup() {
copyResources("functionalTest/scenarioProject", "")
runTasksSuccessfully('clean') //delete accidental output when previously importing SimpleBoot into Idea to tweak it
}
def "should pass basic flow"() {
def "should pass basic flow for Spock"() {
given:
assert fileExists('build.gradle')
expect:
runTasksSuccessfully('check')
}
def "should pass basic flow for JUnit"() {
given:
assert fileExists('build.gradle')
expect:
switchToJunitTestFramework()
runTasksSuccessfully('check')
}
}

View File

@@ -1,6 +1,5 @@
package com.blogspot.toomuchcoding.frauddetection;
import org.glassfish.jersey.client.HttpUrlConnectorProvider;
import org.glassfish.jersey.server.ResourceConfig;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;

View File

@@ -0,0 +1,70 @@
package com.blogspot.toomuchcoding;
import com.blogspot.toomuchcoding.frauddetection.Application;
import com.blogspot.toomuchcoding.frauddetection.FraudRestApplication;
import org.eclipse.jetty.server.Server;
import org.glassfish.jersey.apache.connector.ApacheConnectorProvider;
import org.glassfish.jersey.client.ClientConfig;
import org.glassfish.jersey.jetty.JettyHttpContainerFactory;
import org.glassfish.jersey.server.ResourceConfig;
import org.junit.AfterClass;
import org.junit.BeforeClass;
import org.springframework.context.annotation.AnnotationConfigApplicationContext;
import javax.ws.rs.client.Client;
import javax.ws.rs.client.ClientBuilder;
import javax.ws.rs.client.WebTarget;
import javax.ws.rs.core.UriBuilder;
import java.net.URI;
import static org.springframework.util.SocketUtils.findAvailableTcpPort;
public abstract class MvcTest {
public static WebTarget webTarget;
private static Server server;
private static Client client;
@BeforeClass
public static void setupTest() {
URI baseUri = UriBuilder.fromUri("http://localhost").port(findAvailableTcpPort(8000)).build();
ResourceConfig resourceConfig = ResourceConfig.forApplication(new FraudRestApplication());
resourceConfig.property("contextConfig", new AnnotationConfigApplicationContext(Application.class));
server = JettyHttpContainerFactory.createServer(baseUri, resourceConfig, true);
ClientConfig clientConfig = new ClientConfig();
clientConfig.connectorProvider(new ApacheConnectorProvider());
client = ClientBuilder.newClient(clientConfig);
webTarget = client.target(baseUri);
try {
server.start();
} catch (Exception e) {
e.printStackTrace();
}
}
@AfterClass
public static void cleanupTest() {
if(client != null) {
client.close();
}
if (server != null) {
try {
server.stop();
} catch (Exception e) {
e.printStackTrace();
}
}
}
public void assertThatRejectionReasonIsNull(Object rejectionReason) {
assert rejectionReason == null;
}
}

View File

@@ -0,0 +1,16 @@
package com.blogspot.toomuchcoding;
import com.jayway.restassured.module.mockmvc.RestAssuredMockMvc;
import org.junit.Before;
public class MvcTest {
@Before
public void setup() {
RestAssuredMockMvc.standaloneSetup(new com.blogspot.toomuchcoding.frauddetection.FraudDetectionController());
}
public void assertThatRejectionReasonIsNull(Object rejectionReason) {
assert rejectionReason == null;
}
}

View File

@@ -0,0 +1,16 @@
package com.blogspot.toomuchcoding;
import com.jayway.restassured.module.mockmvc.RestAssuredMockMvc;
import org.junit.Before;
public class MvcTest {
@Before
public void setup() {
RestAssuredMockMvc.standaloneSetup(new com.blogspot.toomuchcoding.frauddetection.FraudDetectionController());
}
public void assertThatRejectionReasonIsNull(Object rejectionReason) {
assert rejectionReason == null;
}
}

View File

@@ -73,6 +73,7 @@ project(':accurest-core') {
compile 'asm:asm:3.3.1'
compile "com.github.tomakehurst:wiremock:$wiremockVersion"
compile "com.blogspot.toomuchcoding:jsonassert:$jsonassertVersion"
compile 'org.assertj:assertj-core:2.3.0'
testCompile 'cglib:cglib-nodep:2.2'
testCompile 'org.objenesis:objenesis:2.1'
testCompile project(':accurest-testing-utils')

View File

@@ -2,4 +2,4 @@ nexusUsername =
nexusPassword =
wiremockVersion = 2.0.5-beta
jsonassertVersion = 0.1.0
jsonassertVersion = 0.1.2