Can I configure HTML and Spring Data REST JSON to the same URI?

I am writing a web application with Spring MVC.

In keeping with the REST principles, I want to use negotiated URIs in my application for the same resources, and use content negotiation to choose whether to return HTML or JSON. A visit /people/bob

in the browser should show my profile page, and getting it with curl

should give me a JSON representation.

However, due to a semantic limitation (bug?) InRequestMappingHandlerMapping

, I cannot "fail" to generic Spring REST data mappings if I define any explicit controller, such as an HTML controller, in the appropriate URI. Apart from manual injection @RestRepositoryController

for each respective HTML controller, is there another easy way to make Spring MVC content consistent between HTML and JSON rendering?


An example of a display that doesn't work:

@BasePathAwareController
class PersonHtmlController {
    @GetMapping(path = '/people/{id}', produces = 'text/html')
    ModelAndView person(@PathVariable Person id) {
        new ModelAndView('person', [person: id])
    }
}

      

This results in expected HTML output, but returns 406 Not Acceptable when I request JSON.

+3


source to share


1 answer


You can go contentnegotiationviewresolver . Below is an example.

@RequestMapping(value = "/users", method = RequestMethod.GET)
public ModelAndView userDetails() {

    ModelAndView modelAndView = new ModelAndView();
    List userDetails = userService.getUserDetails();
    modelAndView.addObject("users", userDetails);
    modelAndView.setViewName("userDetails");
    return modelAndView;

}

      

So whenever a request comes from /users

then the html page will be rendered and when the request comes like /users.json

then a JSON response is generated.



You can customize it as follows by overriding the following method, extending the WebMvcConfigurerAdapter provided by Spring.

@Override
public void configureViewResolvers(ViewResolverRegistry registry) {

    registry.jsp("/WEB-INF/jsp/", ".jsp").viewClass(JstlView.class);
    registry.enableContentNegotiation(
            new MappingJackson2JsonView()
    );

}

      

Hope this helps. Help: Example of Presenting Content View Context

0


source







All Articles