I have several PJO's that represent a response object from an Apache CXF web service (2.7.2). All my root element classes are annotated with @XmlRootElement
.
Here are the POJO classes:
@XmlRootElement(name="SearchResponse")
public class SearchResponse extends Response {
private Listing[] listings;
private SearchSummary summary;
...
}
and
@XmlRootElement(name="SearchResponseRestricted")
public class SearchResponseRestricted extends Response {
private ListingRestricted[] listings;
private SearchSummary summary;
...
}
Using @AutoWired public RestTemplate getRESTClient();
, I can succesfully call the method that returns the SearchResponseRestricted
result, but not the SearchResponse
.
SearchResponseRestricted response = getRESTClient().postForObject(getUrlForJSON()+"/findRestricted", generateJSONRequest(request), SearchResponseRestricted.class); <-- Success
The above succeeds, whereas the following fails to deserialize:
SearchResponse response = getRESTClient().postForObject(getUrlForJSON()+"/find", generateJSONRequest(request), SearchResponse.class); <-- Fails
generateJSONRequest for brevity:
public HttpEntity<Object> generateJSONRequest(Object object) {
HttpHeaders headers = new HttpHeaders();
headers.setContentType(MediaType.APPLICATION_JSON);
headers.setAccept(Arrays.asList(MediaType.APPLICATION_JSON));
return new HttpEntity<Object>(object, headers);
}
It's worth noting, BOTH method calls return JSON back from the Web Service and the JSON data looks to be representative of the Classes that should be deserialized
When the method that fails to deserialize is called, I get the following exception:
org.springframework.web.client.RestClientException: Could not extract response: no suitable HttpMessageConverter found for response type [class com.pkg.ws.pub.SearchResponse] and content type [application/json] at org.springframework.web.client.HttpMessageConverterExtractor.extractData(HttpMessageConverterExtractor.java:108) at org.springframework.web.client.RestTemplate.doExecute(RestTemplate.java:535) at org.springframework.web.client.RestTemplate.execute(RestTemplate.java:489) at org.springframework.web.client.RestTemplate.postForObject(RestTemplate.java:318) at com.pkg.ws.service.SearchServiceWSTest.testFind(SearchServiceWSTest.java:362) at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57) at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) at java.lang.reflect.Method.invoke(Method.java:606) at junit.framework.TestCase.runTest(TestCase.java:176) at junit.framework.TestCase.runBare(TestCase.java:141) at junit.framework.TestResult$1.protect(TestResult.java:122) at junit.framework.TestResult.runProtected(TestResult.java:142) at junit.framework.TestResult.run(TestResult.java:125) at junit.framework.TestCase.run(TestCase.java:129) at junit.framework.TestSuite.runTest(TestSuite.java:255) at junit.framework.TestSuite.run(TestSuite.java:250) at org.junit.internal.runners.JUnit38ClassRunner.run(JUnit38ClassRunner.java:84) at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:50) at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38) at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:467) at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:683) at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:390) at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:197)
Can anyone point me in the right direction or suggest what I may be overlooking?
So I figured out what was wrong. On the failing class, the Listing
object had a field in it that subclassed an abstract class ( Region
)
I ended up simply having to add a few extra annotations listing the known subclasses:
@XmlSeeAlso({RegionAlt.class,RegionGeneric.class,RegionLBA.class,RegionGeom.class,RegionLoc.class,RegionMulti.class,RegionRad.class,RegionStyle.class,RegionPC.class,RegionHi.class,RegionIntersec.class})
@XmlRootElement
@XmlAccessorType(XmlAccessType.FIELD)
public abstract class Region extends .... implements... {
...
}
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.