Reputation: 90
I know multiple posts regarding similar issue present on StackOverflow already and I have also gone through some posts and tried to solve my problem but facing others issue. I'll walk through my implementations and explain challenges faced. Please guide me.
Request Header: 'Content-Type: application/json','Accept: "text/html,application/xml;q=0.9,application/xhtml+xml,text/xml;q=0.9,text/plain;q=0.8,image/png,*/*;q=0.5,application/json;charset=UTF-8"
API call: ResponseEntity<String> responseEntity = restTemplate.exchange(url, method, httpEntity, String.class, paramMap);
Responding API: Content-Type: application/json
org.springframework.web.client.RestClientException: Could not extract response: no suitable HttpMessageConverter found for response type [class java.lang.String] and content type [application/json]
RestTemplate restTemplate = new RestTemplate();
MappingJackson2HttpMessageConverter jackson2Converter = new MappingJackson2HttpMessageConverter();
jackson2Converter.setSupportedMediaTypes(Collections.singletonList(MediaType.ALL));
List<HttpMessageConverter<?>> httpMessageConverters = restTemplate.getMessageConverters();
httpMessageConverters.add(jackson2Converter);
restTemplate.setMessageConverters(httpMessageConverters);
After this change, I started getting, below exception:
java.util.ConcurrentModificationException: null at java.util.ArrayList$Itr.checkForComodification(ArrayList.java:901) at java.util.ArrayList$Itr.next(ArrayList.java:851) at org.springframework.web.client.RestTemplate$AcceptHeaderRequestCallback.doWithRequest(RestTemplate.java:730) at org.springframework.web.client.RestTemplate$HttpEntityRequestCallback.doWithRequest(RestTemplate.java:795) at org.springframework.web.client.RestTemplate.doExecute(RestTemplate.java:617) at org.springframework.web.client.RestTemplate.execute(RestTemplate.java:588) at org.springframework.web.client.RestTemplate.exchange(RestTemplate.java:507) at
To solve the above problem, I did below changes:
requestHeaders.set("Accept", MediaType.APPLICATION_JSON_VALUE);
RestTemplate restTemplate = getRestTemplate();
List<HttpMessageConverter<?>> httpMessageConverters = getHttpMessageConverters();
restTemplate.setMessageConverters(httpMessageConverters);
ResponseEntity<String> responseEntity = restTemplate.exchange(url, method, httpEntity, String.class, paramMap);
private List<HttpMessageConverter<?>> getHttpMessageConverters() {
StringHttpMessageConverter stringConverter = new StringHttpMessageConverter();
stringConverter.setSupportedMediaTypes(Collections.singletonList(MediaType.ALL));
MappingJackson2HttpMessageConverter jackson2Converter = new MappingJackson2HttpMessageConverter();
jackson2Converter.setSupportedMediaTypes(Collections.singletonList(MediaType.ALL));
return new ArrayList<>(Arrays.asList(jackson2Converter, stringConverter));
}
After the above changes I started getting below exception:
Could not read document: Can not deserialize instance of java.lang.String out of START_OBJECT token\n at [Source: java.io.PushbackInputStream@99ef5fc; line: 1, column: 1]; nested exception is com.fasterxml.jackson.databind.JsonMappingException: Can not deserialize instance of java.lang.String out of START_OBJECT token\n at [Source: java.io.PushbackInputStream@99ef5fc; line: 1, column: 1]","context":"default","exception":"org.springframework.http.converter.HttpMessageNotReadableException: Could not read document: Can not deserialize instance of java.lang.String out of START_OBJECT token\n at [Source: java.io.PushbackInputStream@99ef5fc; line: 1, column: 1]; nested exception is com.fasterxml.jackson.databind.JsonMappingException: Can not deserialize instance of java.lang.String out of START_OBJECT token\n at [Source: java.io.PushbackInputStream@99ef5fc; line: 1, column: 1]\n\tat org.springframework.http.converter.json.AbstractJackson2HttpMessageConverter.readJavaType(AbstractJackson2HttpMessageConverter.java:227)\n\tat org.springframework.http.converter.json.AbstractJackson2HttpMessageConverter.read(AbstractJackson2HttpMessageConverter.java:212)\n\tat org.springframework.web.client.HttpMessageConverterExtractor.extractData(HttpMessageConverterExtractor.java:95)\n\tat org.springframework.web.client.RestTemplate$ResponseEntityResponseExtractor.extractData(RestTemplate.java:884)\n\tat org.springframework.web.client.RestTemplate$ResponseEntityResponseExtractor.extractData(RestTemplate.java:868)\n\tat org.springframework.web.client.RestTemplate.doExecute(RestTemplate.java:622)\n\tat org.springframework.web.client.RestTemplate.execute(RestTemplate.java:588)\n\tat org.springframework.web.client.RestTemplate.exchange(RestTemplate.java:507)\n\tat
Please let me know, where I am doing wrong and what is the gap in my understanding and implementation. Thanks in advance!!
Upvotes: 2
Views: 27209
Reputation: 141
By default, the Spring RestTemplate will configure itself with a series of HttpMessageConverters based on what is available in the classpath.
Since you don't appear to be using a custom Jackson ObjectMapper in your MappingJackson2HttpMessageConverter, you don't actually need to configure one. In fact, the only thing you're doing for your message converter is invoking the following:
jackson2Converter.setSupportedMediaTypes(Collections.singletonList(MediaType.ALL));
Which, as I understand it, is used to indicate that this message converter is capable of converting all media types (which is not true).
I suspect that all you really need is this:
RestTemplate restTemplate = getRestTemplate();
ResponseEntity<String> responseEntity = restTemplate.exchange(url, method, httpEntity, String.class, paramMap);
However, even then it might not work since you're providing the following accept criteria in your request:
Accept: "text/html,application/xml;q=0.9,application/xhtml+xml,text/xml;q=0.9,text/plain;q=0.8,image/png,*/*;q=0.5,application/json;charset=UTF-8"
I would try excluding the accept header first, and if that doesn't work I would try setting it to application/json.
Upvotes: 1