Expose return-value-handlers in mvc namespace

Mirroring the MvcConfigurer#addCustomReturnValueHandlers callback which
allows for providing a list of HandlerMethodReturnValueHandler types

git-svn-id: https://src.springframework.org/svn/spring-framework/trunk@4271 50f2f4bb-b051-0410-bef5-90022cba6387
This commit is contained in:
Chris Beams 2011-05-06 19:13:44 +00:00
parent 9e0b7303b4
commit fc3ccd1052
4 changed files with 84 additions and 10 deletions

View File

@ -124,6 +124,7 @@ class AnnotationDrivenBeanDefinitionParser implements BeanDefinitionParser {
ManagedList<?> messageConverters = getMessageConverters(element, source, parserContext);
ManagedList<?> argumentResolvers = getArgumentResolvers(element, source, parserContext);
ManagedList<?> returnValueHandlers = getReturnValueHandlers(element, source, parserContext);
RootBeanDefinition methodAdapterDef = new RootBeanDefinition(RequestMappingHandlerAdapter.class);
methodAdapterDef.setSource(source);
@ -133,6 +134,9 @@ class AnnotationDrivenBeanDefinitionParser implements BeanDefinitionParser {
if (argumentResolvers != null) {
methodAdapterDef.getPropertyValues().add("customArgumentResolvers", argumentResolvers);
}
if (returnValueHandlers != null) {
methodAdapterDef.getPropertyValues().add("customReturnValueHandlers", returnValueHandlers);
}
String methodAdapterName = parserContext.getReaderContext().registerWithGeneratedName(methodAdapterDef);
RootBeanDefinition csInterceptorDef = new RootBeanDefinition(ConversionServiceExposingInterceptor.class);
@ -228,6 +232,14 @@ class AnnotationDrivenBeanDefinitionParser implements BeanDefinitionParser {
return null;
}
private ManagedList<?> getReturnValueHandlers(Element element, Object source, ParserContext parserContext) {
Element handlersElement = DomUtils.getChildElementByTagName(element, "return-value-handlers");
if (handlersElement != null) {
return extractBeanSubElements(handlersElement, parserContext);
}
return null;
}
private ManagedList<?> getMessageConverters(Element element, Object source, ParserContext parserContext) {
Element convertersElement = DomUtils.getChildElementByTagName(element, "message-converters");
ManagedList<? super Object> messageConverters = new ManagedList<Object>();

View File

@ -60,7 +60,27 @@
<xsd:element ref="beans:bean" minOccurs="1" maxOccurs="unbounded">
<xsd:annotation>
<xsd:documentation><![CDATA[
The HttpMessageConverter bean definition.
The HandlerMethodArgumentResolver or WebArgumentResolver bean definition.
]]></xsd:documentation>
</xsd:annotation>
</xsd:element>
</xsd:sequence>
</xsd:complexType>
</xsd:element>
<xsd:element name="return-value-handlers" minOccurs="0">
<xsd:annotation>
<xsd:documentation><![CDATA[
Configures one or more HandlerMethodReturnValueHandler types to use for handling the return value from handler methods.
Using this configuration element is optional.
Using it does not override the built-in support for handling return values.
]]></xsd:documentation>
</xsd:annotation>
<xsd:complexType>
<xsd:sequence>
<xsd:element ref="beans:bean" minOccurs="1" maxOccurs="unbounded">
<xsd:annotation>
<xsd:documentation><![CDATA[
The HandlerMethodReturnValueHandler bean definition.
]]></xsd:documentation>
</xsd:annotation>
</xsd:element>

View File

@ -37,6 +37,7 @@ import org.springframework.web.bind.support.WebDataBinderFactory;
import org.springframework.web.context.request.NativeWebRequest;
import org.springframework.web.context.support.GenericWebApplicationContext;
import org.springframework.web.method.support.HandlerMethodArgumentResolver;
import org.springframework.web.method.support.HandlerMethodReturnValueHandler;
import org.springframework.web.method.support.ModelAndViewContainer;
import org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter;
import org.springframework.web.servlet.mvc.method.annotation.ExceptionHandlerExceptionResolver;
@ -96,6 +97,20 @@ public class AnnotationDrivenBeanDefinitionParserTests {
assertTrue(resolvers.get(1) instanceof TestHandlerMethodArgumentResolver);
}
@SuppressWarnings("unchecked")
@Test
public void testReturnValueHandlers() {
loadBeanDefinitions("mvc-config-return-value-handlers.xml");
RequestMappingHandlerAdapter adapter = appContext.getBean(RequestMappingHandlerAdapter.class);
assertNotNull(adapter);
Object value = new DirectFieldAccessor(adapter).getPropertyValue("customReturnValueHandlers");
assertNotNull(value);
assertTrue(value instanceof List);
List<HandlerMethodReturnValueHandler> handlers = (List<HandlerMethodReturnValueHandler>) value;
assertEquals(1, handlers.size());
assertEquals(TestHandlerMethodReturnValueHandler.class, handlers.get(0).getClass());
}
private void loadBeanDefinitions(String fileName) {
XmlBeanDefinitionReader reader = new XmlBeanDefinitionReader(appContext);
reader.loadBeanDefinitions(new ClassPathResource(fileName,
@ -141,6 +156,19 @@ class TestHandlerMethodArgumentResolver implements HandlerMethodArgumentResolver
}
}
class TestHandlerMethodReturnValueHandler implements HandlerMethodReturnValueHandler {
public boolean supportsReturnType(MethodParameter returnType) {
return false;
}
public void handleReturnValue(Object returnValue,
MethodParameter returnType, ModelAndViewContainer mavContainer,
NativeWebRequest webRequest) throws Exception {
}
}
class TestMessageCodesResolver implements MessageCodesResolver {
public String[] resolveMessageCodes(String errorCode, String objectName) {

View File

@ -0,0 +1,14 @@
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:mvc="http://www.springframework.org/schema/mvc"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc-3.1.xsd">
<mvc:annotation-driven>
<mvc:return-value-handlers>
<bean class="org.springframework.web.servlet.config.TestHandlerMethodReturnValueHandler"/>
</mvc:return-value-handlers>
</mvc:annotation-driven>
</beans>