SpringBoot中SpringMVC的自動配置以及擴充套件
一、問題引入
我們在SSM中使用SpringMVC的時候,需要由我們自己寫SpringMVC的配置檔案,需要用到什麼就要自己配什麼,配置起來也特別的麻煩。我們使用SpringBoot的時候沒有進行配置,直接就能進行使用,這是為什麼呢?
這是因為SpringBoot為我們自動配置好了SpringMVC
1)、我們首先參照官網來看一下關於SpringMVC的自動配置
https://docs.spring.io/spring-boot/docs/2.2.1.RELEASE/reference/htmlsingle/#boot-features-developing-web-applications
Spring MVC Auto-configuration
Spring Boot provides auto-configuration for Spring MVC that works well with most applications.
The auto-configuration adds the following features on top of Spring’s defaults:
-
Inclusion of ContentNegotiatingViewResolver and BeanNameViewResolver beans.
-
- 自動配置了ViewResolver(檢視解析器:根據方法的返回值得到檢視物件(View),檢視物件決定如何渲染(轉發?重定向?))
- ContentNegotiatingViewResolver:組合所有的檢視解析器的;
-
- ==如何定製:我們可以自己給容器中新增一個檢視解析器;自動的將其組合進來
-
Support for serving static resources, including support for WebJars (covered later in this document)).
靜態資原始檔夾路徑.webjars
- Automatic registration of Converter, GenericConverter, and Formatter beans.
自動註冊了Converter, GenericConverter, and Formatter等
-
- **Converter:轉換器,**比如也面提交的是一個數字,但是頁面的數字是文字型別的,通過轉換器,就能轉換成Integer型別
- Formatter :格式化器,2020-1-1===Date;
-
Support for HttpMessageConverters (covered later in this document).
-
- HttpMessageConverter:SpringMVC用來轉換Http請求和響應的;
- HttpMessageConverter是從容器中確定;獲取所有的HttpMessageConverter;
自己給容器中新增HttpMessageConverter,只需要將自己的元件註冊容器中(@Bean,@Component)
- Automatic registration of MessageCodesResolver (covered later in this document).
定義錯誤程式碼生成規則
- Static index.html support.靜態首頁訪問
- Custom Favicon support (covered later in this document).
- Automatic use of a ConfigurableWebBindingInitializer bean (covered later in this document).
我們可以配置一個ConfigurableWebBindingInitializer來替換預設的;(新增到容器)
初始化WebDataBinder;
請求資料=====JavaBean;
If you want to keep Spring Boot MVC features and you want to add additional MVC configuration (interceptors, formatters, view controllers, and other features), you can add your own @Configuration class of type WebMvcConfigurer but without @EnableWebMvc. If you wish to provide custom instances of RequestMappingHandlerMapping, RequestMappingHandlerAdapter, or ExceptionHandlerExceptionResolver, you can declare a WebMvcRegistrationsAdapter instance to provide such components.
2、擴充套件SpringMVC
編寫一個配置類(@Configuration),是WebMvcConfigurerAdapter型別;不能標註@EnableWebMvc;
If you want to take complete control of Spring MVC, you can add your own @Configuration annotated with @EnableWebMvc
3.全面接管SpringMVC
為什麼@EnableWebMvc自動配置就失效了?
1)@EnableWebMvc的核心
@Import(DelegatingWebMvcConfiguration.class)
public @interface EnableWebMvc {
2)、
@Configuration
public class DelegatingWebMvcConfiguration extends WebMvcConfigurationSupport {
3)、
@Configuration
@ConditionalOnWebApplication
@ConditionalOnClass({ Servlet.class, DispatcherServlet.class,
WebMvcConfigurerAdapter.class })
//容器中沒有這個元件的時候,這個自動配置類才生效
@ConditionalOnMissingBean(WebMvcConfigurationSupport.class)
@AutoConfigureOrder(Ordered.HIGHEST_PRECEDENCE + 10)
@AutoConfigureAfter({ DispatcherServletAutoConfiguration.class,
ValidationAutoConfiguration.class })
public class WebMvcAutoConfiguration {
4)、@EnableWebMvc將WebMvcConfigurationSupport元件匯入進來;
5)、匯入的WebMvcConfigurationSupport只是SpringMVC最基本的功能;
4.原理
關於ContentNegotiatingViewResolver
我們點進這個ContentNegotiatingViewResolver ,在下面有一個resolveViewName方法
那麼是怎麼樣獲取候選的檢視物件的呢?
我們點進getCandidateViews這個方法
那麼這個組合邏輯又是什麼呢?
返回到我們這裡
看到首先是new了一個ContentNegotiatingViewResolver物件
我們點進去,
我們所需要的ViewResolvers是從哪裡拿到的呢?
我們接著往下邊看
我們看到,這裡有個初始化方法,裡邊利用BeanFactoryUtils工具,從容器中獲取所有的檢視解析器,把這些檢視解析器就作為要組合的所有檢視解析器。
那麼如何定製我們自己的檢視解析器呢,通過上面的講解,就是:我們只需要自己給容器中新增一個檢視解析器;然後ContentNegotiatingViewResolver就會將其
組合進來。
我們下面舉個簡單的例子給大家演示一下
為了方便,我們就在在SpringBoot的啟動類中建立一個ViewResolver並將其新增到容器中
那麼我們怎麼判斷是否其作用了呢,我們知道,檢視解析器都會被DisPatcherServlet所掃描到,所有的請求都會被DisPatcherServlet類中的doDispatch方法所攔截
在doDispatch方法上打一個斷點,debug執行,隨便訪問一個url,就能看到結果如下。
結果我們發現,我們自己加入的ViewResovler確實生效了