Ответ службы REST на основе параметра принятия
Я ищу, чтобы создать REST-сервис, совместимый с XML, а также JSON Response. С идентификатором URI для обоих. Мне нужно предоставить ответ на основе заголовка принятия.
Возможно ли это с одним URI? Если возможно, как мне установить @Produces?
2 ответа
Чтение ага @Produces
:
Определяет тип (типы) мультимедиа, которые могут создавать методы класса ресурса или {@link javax.ws.rs.ext.MessageBodyWriter}. * Если не указан, то контейнер будет предполагать, что может быть произведен любой тип.
Это означает, что эта аннотация просто уменьшает количество поддерживаемых типов мультимедиа. В противном случае выбор делается автоматически.
Интерфейс MessageBodyWriter
имеет много реализаций для разных типов медиа. Конкретная реализация выбрана в MessageBodyFactory
:
public <T> MediaType getMessageBodyWriterMediaType(Class<T> c, Type t,
Annotation[] as, List<MediaType> acceptableMediaTypes) {
for (MediaType acceptable : acceptableMediaTypes) {
for (MessageBodyWriterPair mbwp : customWriterListProviders) {
for (MediaType mt : mbwp.types) {
if (mt.isCompatible(acceptable) &&
mbwp.mbw.isWriteable(c, t, as, acceptable)) {
return MediaTypes.mostSpecific(mt, acceptable);
}
}
}
......................
Как мы видим, первый поставщик, который поддерживает первый из acceptableMediaTypes
выбран. Хотя имхо название acceptableMediaTypes
Это понятно, я продолжил свое открытие и нашел единственное место, которое вызывает этот метод:
contentType = getMessageBodyWorkers().getMessageBodyWriterMediaType(
entity.getClass(),
entityType,
annotations,
request.getAcceptableMediaTypes());
где request
тип ContainerRequest
,
Вот код getAcceptableMediaTypes()
public List<MediaType> getAcceptableMediaTypes() {
if (accept == null || headersModCount != headers.getModCount())
accept = new ArrayList<MediaType>(HttpHelper.getAccept(this));
return accept;
}
Как мы видим, список типов медиа заполнен результатом HttpHelper.getAccept(this)
:
final String accept = request.getHeaderValue(HttpHeaders.ACCEPT);
Итог: да, тип медиа выбирается автоматически в соответствии с заголовком HTTP Accept
если жестко закодированная аннотация @Produces
ограничивает это.
@Produces({"application/xml", "application/json"})
Для реализаций JAX-RS...
Давным-давно, что я использовал его, но я помню - и все еще могу подать заявку на определенные реализации - что вам нужно добавить настроенный MediaConfig в ваше приложение. Но он определенно встроен для JEE6/7.
И в то время я настроил, чтобы уважать расширение файла в запросе URI... Может быть, заголовок всегда работал.
Изменить: Только что искал, вероятно, не называется MediaConfig, я вернусь, когда я найду / запомню, и если это все еще требуется.