Spring 3.1 или более поздняя версия @RequestMapping потребляет/производит

У меня есть вопрос относительно потребления и производства части @RequestMapping. У меня есть конечная точка, которую я хочу принимать как JSON, так и XML и возвращать JSON при передаче JSON и возвращать XML при передаче XML. Есть ли что-то особенное, что мне нужно сделать, чтобы это работало?

Пример кода приведен ниже.

@RequestMapping(value = "/something", method = PUT, 
                consumes = {APPLICATION_JSON_VALUE, APPLICATION_XML_VALUE}, 
                produces = {APPLICATION_JSON_VALUE, APPLICATION_XML_VALUE})
public SomeObject updateSomeObject(SomeObject acct) {
    return doStuff(acct);
}

Будет ли это работать так, как я ожидаю, или мне нужны две конечные точки updateSomeObjectXML и updateSomeObjectJson для обработки обоих случаев?

Спасибо, Майк


person Mike Baglio Jr.    schedule 20.10.2014    source источник


Ответы (3)


Статья из блога Spring — Согласование контента с использованием Spring MVC — предоставляет подробную информацию о том, как согласование содержимого работает с Spring MVC, вкратце, если вы хотите, чтобы одна и та же конечная точка обрабатывала XML и JSON, ваше сопоставление правильное, резюмируя из статьи:

  1. Используйте расширение пути - вы можете отправить json на /something.json и xml на /something.xml и ожидать того же на обратном пути.

  2. Используйте заголовок Accept, используйте значение application/json или application/xml и используйте Content-Type для указания типа отправляемого мультимедиа.

person Biju Kunjummen    schedule 20.10.2014

Краткий ответ:
Аннотируйте метод с помощью @ResponseBody, а параметр метода с помощью @RequestBody, и он будет работать (нет необходимости в двух методах).

Объяснение.
Во-первых, атрибуты производства и потребления используются для ограничить типы сопоставления. По умолчанию будет использоваться первый найденный HttpMessageConverter, соответствующий запрошенному типу мультимедиа.

Во-вторых, клиент запрашивает тип мультимедиа, указав тип мультимедиа в:
- Принять заголовок запроса
- суфикс URL (http : //....//some .xml => запрошен тип носителя "application/xml")
- параметр формата URL (.../some ?формат=XLS)

В-третьих, produces в сочетании с @ResponseBody создаст объект в запрошенном типе носителя (хорошо для запросов GET, когда вам нужно отправить что-то обратно клиенту), и consumes в сочетании с @RequestBody будет потреблять объект с запрошенным типом носителя (хорошо для запросов POST, когда вам нужно что-то получить от клиента).

В-четвертых, когда @ResponseBody не используется, HttpMessageConverters не используются. Вместо этого ViewResolvers срабатывают и создают представление (HTML, PDF...), а тип возвращаемого значения должен соответствовать правилам, которые сопровождают ViewResolvers (дополнительные сведения см. в сопоставителе представлений по умолчанию и InternalResourceViewResolver).

Надеюсь, поможет.

Другие источники:
http://docs.spring.io/spring/docs/current/javadoc-api/org/springframework/web/bind/annotation/RequestMapping.html#consumes-- http://spring.io/blog/2013/05/11/content-negotiation-using-spring-mvc

person despot    schedule 28.02.2015

Что ж,

потребляет/производит принимает String[] в качестве параметра (см. RequestMapping из документации Spring), поэтому я считаю, что это сработает. Вы также можете попробовать headers = "content-type=application/json,application/xml".

person freakman    schedule 20.10.2014
comment
Я. Мой вопрос заключается в том, как узнать, какие продукты он будет производить в любой момент времени. Это настраивается или автоматически? И как он автоматически выбирает? Если он указан как потребитель JSON, XML и обычного текста, но как производитель JSON и XML, какой тип он вернет, когда придет обычный текст? - person Mike Baglio Jr.; 20.10.2014
comment
он, вероятно, проверит, какой заголовок «accepts» был установлен для запроса, а затем использует сериализатор json/xml из пути к классам. - person freakman; 21.10.2014