Programmatically register'ing WebMvcConfigurationSupport instead of @Configuration

StackOverflow https://stackoverflow.com/questions/22223442

  •  10-06-2023
  •  | 
  •  

Pergunta

[This question is similar to "Preventing a @EnableWebMvc-annotated class from being picked up by @ComponentScan", only with a different attack vector to the problem, which I got a problem with in Spring 4]

Since @ComponentScan finds all @Configuration instances, it also picks up my extension of WebMvcConfigurationSupport which is what I want in servlet environment. But in integration test mode, I don't want that, since it complains about a ServletContext not being present.

java.lang.IllegalStateException: Failed to load ApplicationContext
    at org.springframework.test.context.CacheAwareContextLoaderDelegate.loadContext(CacheAwareContextLoaderDelegate.java:99)
    at ...
Caused by: java.lang.IllegalArgumentException: A ServletContext is required to configure default servlet handling
    at org.springframework.util.Assert.notNull(Assert.java:112)
    at org.springframework.web.servlet.config.annotation.DefaultServletHandlerConfigurer.(DefaultServletHandlerConfigurer.java:54)
    at org.springframework.web.servlet.config.annotation.WebMvcConfigurationSupport.defaultServletHandlerMapping(WebMvcConfigurationSupport.java:329)
    at ...

I used to fix this by instead of letting it be found by @ComponentScan by also having the @Configuration annotation, I directly include it using AnnotationConfigWebApplicationContext.register(thatClass), code which is not run during integration test setup.

This worked just fine until I upgraded to Spring 4.0.2, where I get a new Exception from a 4.0 class CompositeUriComponentsContributor:

Caused by: java.lang.IllegalArgumentException: 'uriComponentsContributors' must not be null
    at org.springframework.util.Assert.notNull(Assert.java:112) ~[spring-core-4.0.2.RELEASE.jar:4.0.2.RELEASE]
    at org.springframework.web.method.support.CompositeUriComponentsContributor.(CompositeUriComponentsContributor.java:88) ~[spring-web-4.0.2.RELEASE.jar:4.0.2.RELEASE]
    at org.springframework.web.servlet.config.annotation.WebMvcConfigurationSupport.mvcUriComponentsContributor(WebMvcConfigurationSupport.java:573) ~[spring-webmvc-4.0.2.RELEASE.jar:4.0.2.RELEASE]
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) ~[na:1.7.0_51]
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57) ~[na:1.7.0_51]
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) ~[na:1.7.0_51]
    at java.lang.reflect.Method.invoke(Method.java:606) ~[na:1.7.0_51]
    at org.springframework.beans.factory.support.SimpleInstantiationStrategy.instantiate(SimpleInstantiationStrategy.java:166) ~[spring-beans-4.0.2.RELEASE.jar:4.0.2.RELEASE]
    ... 34 common frames omitted

So apparently this for some reason now needs to be "@Configuration-found", instead of being included by a register call.

Why is that? How can I get this fixed? I do understand that I can move it out of the @ComponentScan "path", but I want to know what happens.

Foi útil?

Solução

Try this: Annotate your integration test classes with @WebAppConfiguration. This will create a mock ServletContext for the Spring MVC setup.

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top