Detect ConfigurableWebBindingInitializer bean and register with MVC

Previously, to use a custom ConfigurableWebBindingInitializer, it was
necessary to extend WebMvcConfigurationSupport and override
getConfigurableWebBindingInitializer. This had the unwanted
side-effect of switching off the auto-configuration of Spring MVC.

This commit updates the auto-configuration to look for a
ConfigurableWebBindingInitializer bean and register it with Spring
MVC.

Closes gh-2526
pull/3622/merge
Andy Wilkinson 9 years ago
parent 511c6d39fa
commit 51dd806a98

@ -27,6 +27,7 @@ import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.springframework.beans.factory.BeanFactory;
import org.springframework.beans.factory.ListableBeanFactory;
import org.springframework.beans.factory.NoSuchBeanDefinitionException;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.autoconfigure.AutoConfigureAfter;
import org.springframework.boot.autoconfigure.AutoConfigureOrder;
@ -56,6 +57,7 @@ import org.springframework.http.converter.HttpMessageConverter;
import org.springframework.validation.DefaultMessageCodesResolver;
import org.springframework.validation.MessageCodesResolver;
import org.springframework.web.accept.ContentNegotiationManager;
import org.springframework.web.bind.support.ConfigurableWebBindingInitializer;
import org.springframework.web.context.request.RequestContextListener;
import org.springframework.web.filter.HiddenHttpMethodFilter;
import org.springframework.web.filter.HttpPutFormContentFilter;
@ -334,6 +336,9 @@ public class WebMvcAutoConfiguration {
@Autowired(required = false)
private WebMvcProperties mvcProperties;
@Autowired
private ListableBeanFactory beanFactory;
@Bean
@Override
public RequestMappingHandlerAdapter requestMappingHandlerAdapter() {
@ -351,6 +356,16 @@ public class WebMvcAutoConfiguration {
return super.requestMappingHandlerMapping();
}
@Override
protected ConfigurableWebBindingInitializer getConfigurableWebBindingInitializer() {
try {
return this.beanFactory.getBean(ConfigurableWebBindingInitializer.class);
}
catch (NoSuchBeanDefinitionException ex) {
return super.getConfigurableWebBindingInitializer();
}
}
}
}

@ -37,6 +37,7 @@ import org.junit.rules.ExpectedException;
import org.springframework.beans.factory.NoSuchBeanDefinitionException;
import org.springframework.boot.autoconfigure.PropertyPlaceholderAutoConfiguration;
import org.springframework.boot.autoconfigure.web.WebMvcAutoConfiguration.WebMvcAutoConfigurationAdapter;
import org.springframework.boot.autoconfigure.web.WebMvcAutoConfigurationTests.CustomConfigurableWebBindingInitializer.CustomWebBindingInitializer;
import org.springframework.boot.context.embedded.AnnotationConfigEmbeddedWebApplicationContext;
import org.springframework.boot.context.embedded.EmbeddedServletContainerCustomizerBeanPostProcessor;
import org.springframework.boot.context.embedded.EmbeddedServletContainerFactory;
@ -52,6 +53,7 @@ import org.springframework.mock.web.MockHttpServletRequest;
import org.springframework.test.util.ReflectionTestUtils;
import org.springframework.util.ReflectionUtils;
import org.springframework.util.StringUtils;
import org.springframework.web.bind.support.ConfigurableWebBindingInitializer;
import org.springframework.web.filter.HttpPutFormContentFilter;
import org.springframework.web.servlet.HandlerAdapter;
import org.springframework.web.servlet.HandlerMapping;
@ -459,6 +461,14 @@ public class WebMvcAutoConfigurationTests {
is(equalTo(1)));
}
@Test
public void customConfigurableWebBindingInitializer() {
load(CustomConfigurableWebBindingInitializer.class);
assertThat(this.context.getBean(RequestMappingHandlerAdapter.class)
.getWebBindingInitializer(),
is(instanceOf(CustomWebBindingInitializer.class)));
}
@SuppressWarnings("unchecked")
private void load(Class<?> config, String... environment) {
this.context = new AnnotationConfigEmbeddedWebApplicationContext();
@ -580,4 +590,19 @@ public class WebMvcAutoConfigurationTests {
}
@Configuration
static class CustomConfigurableWebBindingInitializer {
@Bean
public ConfigurableWebBindingInitializer customConfigurableWebBindingInitializer() {
return new CustomWebBindingInitializer();
}
static class CustomWebBindingInitializer extends
ConfigurableWebBindingInitializer {
}
}
}

@ -1216,6 +1216,7 @@ The auto-configuration adds the following features on top of Spring's defaults:
* Automatic registration of `MessageCodesResolver` (see below).
* Static `index.html` support.
* Custom `Favicon` support.
* Automatic use of a `ConfigurableWebBindingInitializer` bean (see below).
If you want to take complete control of Spring MVC, you can add your own `@Configuration`
annotated with `@EnableWebMvc`. If you want to keep Spring Boot MVC features, and
@ -1345,6 +1346,13 @@ https://spring.io/blog/2014/07/24/spring-framework-4-1-handling-static-web-resou
and in Spring Framework's {spring-reference}/#mvc-config-static-resources[reference documentation].
====
[[boot-features-spring-mvc-web-binding-initializer]]
==== ConfigurableWebBindingInitializer
Spring MVC uses a `WebBindingInitializer` to initialize a `WebDataBinder` for a particular
request. If you create your own `ConfigurableWebBindingInitializer` `@Bean`, Spring Boot
will automatically configure Spring MVC to use it.
[[boot-features-spring-mvc-template-engines]]

Loading…
Cancel
Save