@EnableWebMvc
@EnableWebMvc 사용법을 알아보자
Last updated
@EnableWebMvc 사용법을 알아보자
Last updated
Dispatcher Servlet의 동작 과정을 살펴보면서 Spring MVC의 전반적인 프로세스를 살펴보았다. 통신 과정에서는 다양한 빈들을 생성하고 사용하였다. 그렇다면 어떤 bean 들이 있었을까?
다음은 스프링 공식 문서에 설명하는 SpringMVC 관련하여 WebApplicationContext 에 등록된 빈들에 대한 정보이다.
Special beans in the WebApplicationContext
Bean type
Explanation
Form the C
part of the MVC.
Handle the execution of a list of pre-processors and post-processors and controllers that will be executed if they match certain criteria (for example, a matching URL specified with the controller).
Resolves view names to views.
A locale resolver is a component capable of resolving the locale a client is using, in order to be able to offer internationalized views
Theme resolver
A theme resolver is capable of resolving themes your web application can use, for example, to offer personalized layouts
multipart file resolver
Contains functionality to process file uploads from HTML forms.
Contains functionality to map exceptions to views or implement other more complex exception handling code.
보통 우리는 Controller까지만 bean으로 등록하지 나머지 bean들은 별도로 등록하지 않았다.
스프링 부트의 경우 spring-boot-starter-web 스타터만 import 해주면 자동 완성으로 인해 아래와 같이 mvc 관련된 bean 들에 대한 설정을 대신 해준다.
ContentNegotiatingViewResolver
(요청이 원하는 뷰를 탐색하고 반환) BeanNameViewResolver
beans (뷰를 찾을 때 빈 이름으로 찾게 도와준다)
정적 리소스를 지원(WebJars)
Converter
, GenericConverter
, Formatter
beans.
HttpMessageConverters
MessageCodesResolver
Static index.html
커스텀 Favicon
ConfigurableWebBindingInitializer
bean
스프링 부트의 자동완성 덕분에 우리는 별다른 bean 설정 없이 mvc 기능을 사용할 수 있다. 하지만 애플리케이션을 개발하다 보면 다양한 요구사항이 발생할 수 있게 되고 우리는 기본 동작하는 빈들을 커스터마이징 하고 싶다면 어떻게 해야 할까?
기존에 설정된 bean 설정을 유지하고 기능을 확장하고 싶다면 @EnableWebMvc
없이 WebMvcConfigurer
타입의@Configuration
클래스를 추가하면 된다.
RequestMappingHandlerMapping
, RequestMappingHandlerAdapter
, MVC 커스트마이징을 하면서 ExceptionHandlerExceptionResolver
인스턴스를 제공하기 원하면, WebMvcRegistrations
타입의 빈을 선언하고 커스텀 인스턴스로 사용 할 수 있다.
Spring MVC 의 완전한 제어를 원한다면 @EnableWebMvc
로 어노테이트된 @Configuration
을 추가할 수 있다. 또는 @Configuration
어노테이트된 DelegatingWebMvcConfiguration
을 사용할 수 있다.
@EnableWebMvc 애노테이션을 살펴보면 해답을 알 수 있다.
EnableWebMvc 애노테이션 내부엔 DelegatingWebMvcConfiguration 클래스를 import한 것을 볼수 있다.
DelegatingWebMvcConfiguration 클래스 내부를 살펴보면 WebMvcConfigurationSupport 클래스를 상속 받아 Web 관련 빈들을 커스터마이징 할 수 있도록 해준다.
위의 코드를 보면 setConfigurers 메소드에서 WebMvcConfigurer 타입의 빈을 모두 주입받아서 WebMvcConfigurerComposite 타입의 객체에 주입하고 있다. 따라서 WebMvcConfigurer 타입의 빈들은 전부 WebMvcConfigurerComposite 객체에 주입이 된다. WebMvcConfigurer 타입의 빈들은 Web 관련 빈들을 초기화할 때 사용된다.
DelegatingWebMvcConfiguration는 WebMvcConfigurer 타입의 빈들을 통해서 등록되는 빈들을 커스터마이징 할 수 있게 해주는 정도의 역할만 하고 있다.
HandlerMapping
RequestMappingHandlerMapping
HandlerMapping
BeanNameUrlHandlerMapping
HandlerMapping
HandlerMapping
HandlerAdapter
RequestMappingHandlerAdapter
HttpRequestHandlerAdapter
SimpleControllerHandlerAdapter
HandlerExceptionResolerComposite
ExceptionHandlerExceptionResolver
ResponseStatusExceptionResolver
DefaultHandlerExceptionResolver
기타
AntPathMather
UrlPathHelper
ContentNegotiationManager
스프링 MVC 자동구성은 WebMvcAutoConfiguration
이 담당한다. 이 구성이 활성화되는 조건 중에 WebMvcConfigurationSupport
타입의 빈을 찾을 수 없을 때 라는 조건이 있다.
바로 이 조건(@ConditionalOnMissingBean(WebMvcConfigurationSupport.class)
) 때문에 이미 빈이 생성되었기 때문에 기본 전략을 참고하지 못한다.
WebMvcConfigurer 인터페이스는 MVC 네임스페이스를 이용한 설정과 동일한 설정을 하는데 필요한 메소드를 정의하고 있다. 위에서 설명했듯이 HttpMessageConverter를 추가할 때 WebMvcConfigurer 인터페이스를 상속한 @Configuration 클래스를 만들고, configureMessageConverters 메소드를 구현해주면 된다. WebMvcConfigurerAdapter는 추상 클래스로 spring 5 이후에는 deprecated 되어 WebMvcConfigurer만 사용하면 된다.
WebMvcConfigurerAdapters는 spring 5 이전에는 많이 사용하였는데 추상클래스로 되어 있기 때문에 사용자가 필요하지 않은 기능들은 구현할 필요가 없기 때문에 WebMvcConfigurerAdapters 클래스 사용을 권장하였다. 그러나 spring 5 부터는 인터페이스의 default method를 제공해주기 때문에 공통 구현을 제공하기 때문에 deprecated 되었다고 한다.
Deprecated. as of 5.0 WebMvcConfigurer has default methods (made possible by a Java 8 baseline) and can be implemented directly without the need for this adapter