March 20, 2012

Controlling message converters with Spring MVC 3.1

In my previous post I talked about how to support both JSON and XML in a Spring MVC web service. The observant reader might have noticed that if a request was made with an Accept header with neither application/json nor application/xml specified then the data was returned in XML. The integration test in the example code used to illustrate this looked like this:

@Test
 public void getUserWithUnsupportedAccept() throws Exception {
  RestTemplate restTemplate = createStringRestTemplate();

  String user = restTemplate.getForObject(new URI(baseUrl + "/123"), String.class);

  logger.debug("Received data as: {}", user);
 }

The code will log the received data and you can see that it is in XML format. The reason for this is how the message converters are added by default. Go check out the Spring source code if you want to know the details.

Now, if you rather want JSON to be the default format then changing the behavior of our web service is simply a matter of defining our own order for the message converters and make sure the JSON converter comes before the Jaxb converter.
We can do this by using the new <mvc:message-converters> configuration element in Spring MVC 3.1. If we change our configuration from this:

<mvc:annotation-driven />

to a configuration that specifies the order of the message converters explicitly like this:

<mvc:annotation-driven>
  <mvc:message-converters>
   <bean class="org.springframework.http.converter.json.MappingJacksonHttpMessageConverter">
   <bean class="org.springframework.http.converter.xml.Jaxb2RootElementHttpMessageConverter">  
  </mvc:message-converters>
</mvc:annotation-driven>

we will get the desired result. If you run the above integration test again you will now see that the data is returned in JSON format.

If you want to prevent any default message converters to be added in addition to the ones you explicitly specify then you can control that with the register-default attribute. An example of that would be:

<mvc:message-converters register-defaults="false">

With the new features in Spring MVC 3.1, controlling message converters has become really easy and we have now enhanced our REST API to return JSON by default.

2 comments:

  1. Hi Daniel,

    I read your previous and this post. I tried to implement the similar thing but unfortunately, it is always returning XML regardless of the message converters defined.

    Any idea?

    ReplyDelete
    Replies
    1. Hi,
      remember that you need to remove the previous line in the example. Otherwise it will interfere.
      Also, it is all based on the accept header so if you are testing with a browser you need to be able to control the headers being sent.

      Delete