Support target type in JsonPath assertions for MockMvc results
This commit picks up where SPR-14498 left off by adding support for an explicit target type when using JsonPath to perform an assertion against the response content using a Hamcrest Matcher. Specifically, there is a new overloaded value(Matcher<T>, Class<T>) method in JsonPathResultMatchers for use with Hamcrest matchers where the target type (i.e., Class<T>) can be specified. Issue: SPR-16587
This commit is contained in:
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2002-2017 the original author or authors.
|
* Copyright 2002-2018 the original author or authors.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
@@ -282,21 +282,21 @@ public class JsonPathExpectationsHelper {
|
|||||||
|
|
||||||
@Nullable
|
@Nullable
|
||||||
private Object evaluateJsonPath(String content) {
|
private Object evaluateJsonPath(String content) {
|
||||||
String message = "No value at JSON path \"" + this.expression + "\"";
|
|
||||||
try {
|
try {
|
||||||
return this.jsonPath.read(content);
|
return this.jsonPath.read(content);
|
||||||
}
|
}
|
||||||
catch (Throwable ex) {
|
catch (Throwable ex) {
|
||||||
|
String message = "No value at JSON path \"" + this.expression + "\"";
|
||||||
throw new AssertionError(message, ex);
|
throw new AssertionError(message, ex);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private Object evaluateJsonPath(String content, Class<?> targetType) {
|
private Object evaluateJsonPath(String content, Class<?> targetType) {
|
||||||
String message = "No value at JSON path \"" + this.expression + "\"";
|
|
||||||
try {
|
try {
|
||||||
return JsonPath.parse(content).read(this.expression, targetType);
|
return JsonPath.parse(content).read(this.expression, targetType);
|
||||||
}
|
}
|
||||||
catch (Throwable ex) {
|
catch (Throwable ex) {
|
||||||
|
String message = "No value at JSON path \"" + this.expression + "\"";
|
||||||
throw new AssertionError(message, ex);
|
throw new AssertionError(message, ex);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2002-2016 the original author or authors.
|
* Copyright 2002-2018 the original author or authors.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
@@ -30,6 +30,7 @@ import org.springframework.test.web.client.RequestMatcher;
|
|||||||
/**
|
/**
|
||||||
* Factory for assertions on the request content using
|
* Factory for assertions on the request content using
|
||||||
* <a href="https://github.com/jayway/JsonPath">JsonPath</a> expressions.
|
* <a href="https://github.com/jayway/JsonPath">JsonPath</a> expressions.
|
||||||
|
*
|
||||||
* <p>An instance of this class is typically accessed via
|
* <p>An instance of this class is typically accessed via
|
||||||
* {@link MockRestRequestMatchers#jsonPath(String, Matcher)} or
|
* {@link MockRestRequestMatchers#jsonPath(String, Matcher)} or
|
||||||
* {@link MockRestRequestMatchers#jsonPath(String, Object...)}.
|
* {@link MockRestRequestMatchers#jsonPath(String, Object...)}.
|
||||||
@@ -70,10 +71,11 @@ public class JsonPathRequestMatchers {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* An overloaded variant of (@link {@link #value(Matcher)} that also
|
* An overloaded variant of {@link #value(Matcher)} that also accepts a
|
||||||
* accepts a target type for the resulting value that the matcher can work
|
* target type for the resulting value that the matcher can work reliably
|
||||||
* reliably against. This can be useful for matching numbers reliably for
|
* against.
|
||||||
* example coercing an integer into a double.
|
* <p>This can be useful for matching numbers reliably — for example,
|
||||||
|
* to coerce an integer into a double.
|
||||||
* @since 4.3.3
|
* @since 4.3.3
|
||||||
*/
|
*/
|
||||||
public <T> RequestMatcher value(final Matcher<T> matcher, final Class<T> targetType) {
|
public <T> RequestMatcher value(final Matcher<T> matcher, final Class<T> targetType) {
|
||||||
|
|||||||
@@ -199,7 +199,7 @@ public abstract class MockRestRequestMatchers {
|
|||||||
* @param expression the JSON path optionally parameterized with arguments
|
* @param expression the JSON path optionally parameterized with arguments
|
||||||
* @param args arguments to parameterize the JSON path expression with
|
* @param args arguments to parameterize the JSON path expression with
|
||||||
*/
|
*/
|
||||||
public static JsonPathRequestMatchers jsonPath(String expression, Object ... args) {
|
public static JsonPathRequestMatchers jsonPath(String expression, Object... args) {
|
||||||
return new JsonPathRequestMatchers(expression, args);
|
return new JsonPathRequestMatchers(expression, args);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2002-2017 the original author or authors.
|
* Copyright 2002-2018 the original author or authors.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
@@ -80,19 +80,40 @@ public class JsonPathResultMatchers {
|
|||||||
/**
|
/**
|
||||||
* Evaluate the JSON path expression against the response content and
|
* Evaluate the JSON path expression against the response content and
|
||||||
* assert the resulting value with the given Hamcrest {@link Matcher}.
|
* assert the resulting value with the given Hamcrest {@link Matcher}.
|
||||||
|
* @see #value(Matcher, Class)
|
||||||
|
* @see #value(Object)
|
||||||
*/
|
*/
|
||||||
public <T> ResultMatcher value(final Matcher<T> matcher) {
|
public <T> ResultMatcher value(Matcher<T> matcher) {
|
||||||
return result -> {
|
return result -> {
|
||||||
String content = getContent(result);
|
String content = getContent(result);
|
||||||
jsonPathHelper.assertValue(content, matcher);
|
jsonPathHelper.assertValue(content, matcher);
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* An overloaded variant of {@link #value(Matcher)} that also accepts a
|
||||||
|
* target type for the resulting value that the matcher can work reliably
|
||||||
|
* against.
|
||||||
|
* <p>This can be useful for matching numbers reliably — for example,
|
||||||
|
* to coerce an integer into a double.
|
||||||
|
* @since 4.3.15
|
||||||
|
* @see #value(Matcher)
|
||||||
|
* @see #value(Object)
|
||||||
|
*/
|
||||||
|
public <T> ResultMatcher value(Matcher<T> matcher, Class<T> targetType) {
|
||||||
|
return result -> {
|
||||||
|
String content = getContent(result);
|
||||||
|
jsonPathHelper.assertValue(content, matcher, targetType);
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Evaluate the JSON path expression against the response content and
|
* Evaluate the JSON path expression against the response content and
|
||||||
* assert that the result is equal to the supplied value.
|
* assert that the result is equal to the supplied value.
|
||||||
|
* @see #value(Matcher)
|
||||||
|
* @see #value(Matcher, Class)
|
||||||
*/
|
*/
|
||||||
public ResultMatcher value(final Object expectedValue) {
|
public ResultMatcher value(Object expectedValue) {
|
||||||
return result -> jsonPathHelper.assertValue(getContent(result), expectedValue);
|
return result -> jsonPathHelper.assertValue(getContent(result), expectedValue);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2002-2017 the original author or authors.
|
* Copyright 2002-2018 the original author or authors.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
@@ -186,7 +186,7 @@ public abstract class MockMvcResultMatchers {
|
|||||||
* @param expression the JSON path expression, optionally parameterized with arguments
|
* @param expression the JSON path expression, optionally parameterized with arguments
|
||||||
* @param args arguments to parameterize the JSON path expression with
|
* @param args arguments to parameterize the JSON path expression with
|
||||||
*/
|
*/
|
||||||
public static JsonPathResultMatchers jsonPath(String expression, Object ... args) {
|
public static JsonPathResultMatchers jsonPath(String expression, Object... args) {
|
||||||
return new JsonPathResultMatchers(expression, args);
|
return new JsonPathResultMatchers(expression, args);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2002-2015 the original author or authors.
|
* Copyright 2002-2018 the original author or authors.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
@@ -18,6 +18,8 @@ package org.springframework.test.web.client.match;
|
|||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
|
||||||
|
import org.hamcrest.Matchers;
|
||||||
|
|
||||||
import org.junit.Test;
|
import org.junit.Test;
|
||||||
|
|
||||||
import org.springframework.mock.http.client.MockClientHttpRequest;
|
import org.springframework.mock.http.client.MockClientHttpRequest;
|
||||||
@@ -55,14 +57,19 @@ public class JsonPathRequestMatchersTests {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@Test(expected = AssertionError.class)
|
||||||
|
public void valueWithMismatch() throws Exception {
|
||||||
|
new JsonPathRequestMatchers("$.str").value("bogus").match(request);
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void value() throws Exception {
|
public void valueWithDirectMatch() throws Exception {
|
||||||
new JsonPathRequestMatchers("$.str").value("foo").match(request);
|
new JsonPathRequestMatchers("$.str").value("foo").match(request);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test(expected = AssertionError.class)
|
@Test // SPR-14498
|
||||||
public void valueNoMatch() throws Exception {
|
public void valueWithNumberConversion() throws Exception {
|
||||||
new JsonPathRequestMatchers("$.str").value("bogus").match(request);
|
new JsonPathRequestMatchers("$.num").value(5.0f).match(request);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@@ -70,8 +77,13 @@ public class JsonPathRequestMatchersTests {
|
|||||||
new JsonPathRequestMatchers("$.str").value(equalTo("foo")).match(request);
|
new JsonPathRequestMatchers("$.str").value(equalTo("foo")).match(request);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test // SPR-14498
|
||||||
|
public void valueWithMatcherAndNumberConversion() throws Exception {
|
||||||
|
new JsonPathRequestMatchers("$.num").value(Matchers.equalTo(5.0f), Float.class).match(request);
|
||||||
|
}
|
||||||
|
|
||||||
@Test(expected = AssertionError.class)
|
@Test(expected = AssertionError.class)
|
||||||
public void valueWithMatcherNoMatch() throws Exception {
|
public void valueWithMatcherAndMismatch() throws Exception {
|
||||||
new JsonPathRequestMatchers("$.str").value(equalTo("bogus")).match(request);
|
new JsonPathRequestMatchers("$.str").value(equalTo("bogus")).match(request);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2002-2016 the original author or authors.
|
* Copyright 2002-2018 the original author or authors.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
@@ -58,14 +58,19 @@ public class JsonPathResultMatchersTests {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test(expected = AssertionError.class)
|
||||||
|
public void valueWithMismatch() throws Exception {
|
||||||
|
new JsonPathResultMatchers("$.str").value("bogus").match(stubMvcResult);
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void value() throws Exception {
|
public void valueWithDirectMatch() throws Exception {
|
||||||
new JsonPathResultMatchers("$.str").value("foo").match(stubMvcResult);
|
new JsonPathResultMatchers("$.str").value("foo").match(stubMvcResult);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test(expected = AssertionError.class)
|
@Test // SPR-16587
|
||||||
public void valueNoMatch() throws Exception {
|
public void valueWithNumberConversion() throws Exception {
|
||||||
new JsonPathResultMatchers("$.str").value("bogus").match(stubMvcResult);
|
new JsonPathResultMatchers("$.num").value(5.0f).match(stubMvcResult);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
@@ -73,8 +78,13 @@ public class JsonPathResultMatchersTests {
|
|||||||
new JsonPathResultMatchers("$.str").value(Matchers.equalTo("foo")).match(stubMvcResult);
|
new JsonPathResultMatchers("$.str").value(Matchers.equalTo("foo")).match(stubMvcResult);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test // SPR-16587
|
||||||
|
public void valueWithMatcherAndNumberConversion() throws Exception {
|
||||||
|
new JsonPathResultMatchers("$.num").value(Matchers.equalTo(5.0f), Float.class).match(stubMvcResult);
|
||||||
|
}
|
||||||
|
|
||||||
@Test(expected = AssertionError.class)
|
@Test(expected = AssertionError.class)
|
||||||
public void valueWithMatcherNoMatch() throws Exception {
|
public void valueWithMatcherAndMismatch() throws Exception {
|
||||||
new JsonPathResultMatchers("$.str").value(Matchers.equalTo("bogus")).match(stubMvcResult);
|
new JsonPathResultMatchers("$.str").value(Matchers.equalTo("bogus")).match(stubMvcResult);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user