Spring MVC 3: возвращение XML через @ResponseBody

Извините за то, что я опубликовал этот вопрос, но я уже довольно давно отлаживаю эту проблему. У меня есть небольшая проблема, пытаясь получить ответ, чтобы вернуть XML на основе объекта:

@RequestMapping(value = "/mylink", method = RequestMethod.GET)
public @ResponseBody SomeObject doIt() {
    ...
}

Прямо сейчас, несмотря на то, что этот API вызывается, моя клиентская сторона вообще не получает XML-ответ. Я читал несколько мест, и мне кажется, что мне нужно настроить маршаллер XML или какой-нибудь определитель XML, но я не уверен, как интегрировать этот фрагмент в мою существующую конфигурацию. В настоящее время у меня есть следующая конфигурация в моем servlet.xml:

<context:component-scan base-package="ss.controller" />

<mvc:annotation-driven />

<mvc:resources location="/resources/" mapping="/resources/**" />

<bean id="viewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver">
    <property name="prefix" value="/WEB-INF/jsp/app/" />
    <property name="suffix" value=".jsp" />
</bean>

Может кто-то любезно опубликовать несколько примеров конфигурации о том, как я могу настроить мой servlet.xml, чтобы это работало? Большое спасибо.

6 ответов

Решение

Это можно сделать, добавив следующую магию в контекст Spring (см. Документы):

<mvc:annotation-driven/>

который, помимо прочего, обеспечивает:

Поддержка чтения и записи XML, если JAXB присутствует в пути к классам.

Если обнаружен JAXB (т. Е. Если вы находитесь на Java6, или у вас есть какая-либо реализация JAXB на вашем пути к классам), это зарегистрирует Jaxb2RootElementHttpMessageConverter с контекстом, и предоставит возможность выплюнуть XML из возвращаемого значения @ResponseBodyАннотированный метод.

Примечание: ваш вопрос вроде как предложил использовать ViewResolver для рендеринга XML, но это не обязательно. @ResponseBody аннотация предназначена для полного обхода слоя представления.

Я решил эту проблему с Spring 3 MVC без MarshallingView

@RequestMapping(value = "actionName.xml", method = RequestMethod.GET)
public HttpEntity<byte[]> getXml(ModelMap map, HttpServletResponse response) {

    String xml = generateSomeXml();

    byte[] documentBody = xml.getBytes();

    HttpHeaders header = new HttpHeaders();
    header.setContentType(new MediaType("application", "xml"));
    header.setContentLength(documentBody.length);
    return new HttpEntity<byte[]>(documentBody, header);
}

это все. Привет

Когда я хочу вернуть XML-представление объектов с помощью Spring, я делаю то, что я определяю MarshallingView, например:

<!-- XML view using a JAXB marshaller -->
<bean id="jaxbView" class="org.springframework.web.servlet.view.xml.MarshallingView">
    <constructor-arg>
        <bean id="jaxb2Marshaller" class="org.springframework.oxm.jaxb.Jaxb2Marshaller">
            <property name="classesToBeBound">
                <list>
                    <value>com.company.AClass</value>
                </list>
            </property>
        </bean>
    </constructor-arg>
</bean>

<!-- Resolve views based on string names -->
<bean class="org.springframework.web.servlet.view.BeanNameViewResolver"/>

Обратите внимание, что существует целый мир альтернатив jaxb. Следующий шаг

@RequestMapping("/request")
public ModelAndView sample() {
    return new ModelAndView("jaxbView", "data", "data_to_be_turned_into_xml");
}

Или, если вы хотите использовать аннотацию ResponseBody, она будет выглядеть так:

@RequestMapping("/request")
@ResponseBody
public void sample() {
    return "data_to_be_turned_into_xml"
}

Обратите внимание, что это требует определения HttpMessageConverter. См. Весеннюю документацию для идеального образца того, как это сделать.

Вам, вероятно, придется либо использовать XML Marshalling View, либо настроить MarshallingHttpMessageConverter,

Вот краткое руководство по использованию@ResponseBody с конвертерами.

Попробуйте добавить produces = MediaType.APPLICATION_XML_VALUEт.е.

@RequestMapping(value = "/mylink", method = RequestMethod.GET, produces = MediaType.APPLICATION_XML_VALUE)

Добавление produces = MediaType.APPLICATION_XML_VALUE в RequestMapping и @XmlRootElement к вершине вашей модели объект должен работать

@RequestMapping(value = "/mylink", method = RequestMethod.GET, produces = MediaType.APPLICATION_XML_VALUE)
public SomeObject doIt(){
    return new SomeObject();
}

@XmlRootElement
public class SomeObject {

}
Другие вопросы по тегам