springboot mvc自动配置(一)自动配置DispatcherServlet和DispatcherServletRegistry
所有文章
https://www.cnblogs.com/lay2017/p/11775787.html
正文
springboot的自动配置基于SPI机制,实现自动配置的核心要点就是添加一个自动配置的类,SpringBoot MVC的自动配置自然也是相同原理。
本文开始,我们将讨论Springboot下Servlet的web实现。所以,先找到对应的自动配置类。
org.springframework.boot.autoconfigure.web.servlet.DispatcherServletAutoConfiguration
DispatcherServletAutoConfiguration自动配置类
我们打开该类
@AutoConfigureOrder(Ordered.HIGHEST_PRECEDENCE)
@Configuration(proxyBeanMethods = false)
@ConditionalOnWebApplication(type = Type.SERVLET)
@ConditionalOnClass(DispatcherServlet.class)
@AutoConfigureAfter(ServletWebServerFactoryAutoConfiguration.class)
public class DispatcherServletAutoConfiguration {
//...
}
1、首先注意到,@Configuration表名这是一个配置类,将会被spring给解析。
2、@ConditionalOnWebApplication意味着当时一个web项目,且是Servlet项目的时候才会被解析。
3、@ConditionalOnClass指明DispatcherServlet这个核心类必须存在才解析该类。
4、@AutoConfigureAfter指明在ServletWebServerFactoryAutoConfiguration这个类之后再解析,设定了一个顺序。
总的来说,这些注解表明了该自动配置类的会解析的前置条件需要满足。
其次,DispatcherServletAutoConfiguration类主要包含了两个内部类,分别是
1、DispatcherServletConfiguration
2、DispatcherServletRegistrationConfiguration
顾名思义,前者是配置DispatcherServlet,后者是配置DispatcherServlet的注册类。什么是注册类?我们知道Servlet实例是要被添加(注册)到如tomcat这样的ServletContext里的,这样才能够提供请求服务。所以,DispatcherServletRegistrationConfiguration将生成一个Bean,负责将DispatcherServlet给注册到ServletContext中。
配置DispatcherServletConfiguration
我们先看看DispatcherServletConfiguration这个配置类
@Configuration(proxyBeanMethods = false)
@Conditional(DefaultDispatcherServletCondition.class)
@ConditionalOnClass(ServletRegistration.class)
@EnableConfigurationProperties({ HttpProperties.class, WebMvcProperties.class })
protected static class DispatcherServletConfiguration { //...
}
@Conditional指明了一个前置条件判断,由DefaultDispatcherServletCondition实现。主要是判断了是否已经存在DispatcherServlet,如果没有才会触发解析。
@ConditionalOnClass指明了当ServletRegistration这个类存在的时候才会触发解析,生成的DispatcherServlet才能注册到ServletContext中。
最后,@EnableConfigrationProperties将会从application.properties这样的配置文件中读取spring.http和spring.mvc前缀的属性生成配置对象HttpProperties和WebMvcProperties。
再看DispatcherServletConfiguration这个内部类的内部代码
@Bean(name = DEFAULT_DISPATCHER_SERVLET_BEAN_NAME)
public DispatcherServlet dispatcherServlet(HttpProperties httpProperties, WebMvcProperties webMvcProperties) {
DispatcherServlet dispatcherServlet = new DispatcherServlet();
dispatcherServlet.setDispatchOptionsRequest(webMvcProperties.isDispatchOptionsRequest());
dispatcherServlet.setDispatchTraceRequest(webMvcProperties.isDispatchTraceRequest());
dispatcherServlet.setThrowExceptionIfNoHandlerFound(webMvcProperties.isThrowExceptionIfNoHandlerFound());
dispatcherServlet.setPublishEvents(webMvcProperties.isPublishRequestHandledEvents());
dispatcherServlet.setEnableLoggingRequestDetails(httpProperties.isLogRequestDetails());
return dispatcherServlet;
} @Bean
@ConditionalOnBean(MultipartResolver.class)
@ConditionalOnMissingBean(name = DispatcherServlet.MULTIPART_RESOLVER_BEAN_NAME)
public MultipartResolver multipartResolver(MultipartResolver resolver) {
// Detect if the user has created a MultipartResolver but named it incorrectly
return resolver;
}
这个两个方法我们比较熟悉了,就是生成了Bean。
dispatcherServlet方法将生成一个DispatcherServlet的Bean对象。比较简单,就是获取一个实例,然后添加一些属性设置。
multipartResolver方法主要是把你配置的MultipartResolver的Bean给重命名一下,防止你不是用multipartResolver这个名字作为Bean的名字。
配置DispatcherServletRegistrationConfiguration
再看注册类的Bean配置
@Configuration(proxyBeanMethods = false)
@Conditional(DispatcherServletRegistrationCondition.class)
@ConditionalOnClass(ServletRegistration.class)
@EnableConfigurationProperties(WebMvcProperties.class)
@Import(DispatcherServletConfiguration.class)
protected static class DispatcherServletRegistrationConfiguration {
//...
}
同样的,@Conditional有一个前置判断,DispatcherServletRegistrationCondition主要判断了该注册类的Bean是否存在。
@ConditionOnClass也判断了ServletRegistration是否存在
@EnableConfigurationProperties生成了WebMvcProperties的属性对象
@Import导入了DispatcherServletConfiguration,也就是我们上面的配置对象。
再看DispatcherServletRegistrationConfiguration的内部实现
@Bean(name = DEFAULT_DISPATCHER_SERVLET_REGISTRATION_BEAN_NAME)
@ConditionalOnBean(value = DispatcherServlet.class, name = DEFAULT_DISPATCHER_SERVLET_BEAN_NAME)
public DispatcherServletRegistrationBean dispatcherServletRegistration(DispatcherServlet dispatcherServlet,
WebMvcProperties webMvcProperties, ObjectProvider<MultipartConfigElement> multipartConfig) {
DispatcherServletRegistrationBean registration = new DispatcherServletRegistrationBean(dispatcherServlet,
webMvcProperties.getServlet().getPath());
registration.setName(DEFAULT_DISPATCHER_SERVLET_BEAN_NAME);
registration.setLoadOnStartup(webMvcProperties.getServlet().getLoadOnStartup());
multipartConfig.ifAvailable(registration::setMultipartConfig);
return registration;
}
内部只有一个方法,生成了DispatcherServletRegistrationBean。核心逻辑就是实例化了一个Bean,设置了一些参数,如dispatcherServlet、loadOnStartup等。
总结
springboot mvc的自动配置类是DispatcherServletAutoConfigration,主要做了两件事:
1)配置DispatcherServlet
2)配置DispatcherServlet的注册Bean
springboot mvc自动配置(一)自动配置DispatcherServlet和DispatcherServletRegistry的更多相关文章
- springboot mvc自动配置(目录)
对于长时间基于spring框架做web开发的我们,springmvc几乎成为了开发普通web项目的标配.本系列文章基于快速启动的springboot,将从源码角度一点点了解springboot中mvc ...
- springboot mvc自动配置(三)初始化mvc的组件
所有文章 https://www.cnblogs.com/lay2017/p/11775787.html 正文 在springboot mvc自动配置的时候,获得了DispatcherServlet和 ...
- 全网最深分析SpringBoot MVC自动配置失效的原因
前言 本来没有计划这一篇文章的,只是在看完SpringBoot核心原理后,突然想到之前开发中遇到的MVC自动失效的问题,虽然网上有很多文章以及官方文档都说明了原因,但还是想亲自看一看,本以为很简单的事 ...
- Springboot MVC 自动配置
Springboot MVC 自动配置 官方文档阅读 https://docs.spring.io/spring-boot/docs/current/reference/html/web.html#w ...
- SpringBoot中对SpringMVC的自动配置
https://docs.spring.io/spring-boot/docs/1.5.10.RELEASE/reference/htmlsingle/#boot-features-developin ...
- SpringBoot | 4.1 SpringMVC的自动配置
目录 前言 1. SpringMVC框架的设计与流程 1.1 SpringMVC框架的示意图 1.2 SpringMVC的组件流程 2. *自动配置的源码分析 2.1 导入Web场景启动器 2.2 找 ...
- springboot web项目创建及自动配置分析(thymeleaf+flyway)
@ 目录 源码分析 webjars thymeleaf thymeleaf语法 springmvc 启动配置原理 集成flyway插件 springboot 创建web项目只需要引入对应的web-st ...
- SpringBoot入门(四)——自动配置
本文来自网易云社区 SpringBoot之所以能够快速构建项目,得益于它的2个新特性,一个是起步依赖前面已经介绍过,另外一个则是自动配置.起步依赖用于降低项目依赖的复杂度,自动配置负责减少人工配置的工 ...
- 接管SpringBoot对Activiti的数据源自动配置
SpringBoot的自动配置真的让人又爱又恨,但还是爱更多一点. SpringBoot想要帮我们自动配置好一切,但是有时候配置的却并不是我们需要的,甚至有时候会默默的坑我们. 我的项目是一个多数据源 ...
随机推荐
- LC 991. Broken Calculator
On a broken calculator that has a number showing on its display, we can perform two operations: Doub ...
- 【转载】 迁移学习简介(tranfer learning)
原文地址: https://blog.csdn.net/qq_33414271/article/details/78756366 土豆洋芋山药蛋 --------------------------- ...
- linux chown 命令用法
[-cfhvR] [--help] [--version] user[:group] file 比如 chown chown root /home 把/home的属主改成root用户使用权限 : ...
- es6 关于map和for of的区别有哪些?
1.es6 关于map和for of的区别有哪些? ——主要想了解一下性能方面的
- Spring 分布式事务详解
在学习分布式事务的过程中会遇到以下关键名词: 相关名词: XA :XA规范的目的是允许多个资源(如数据库,应用服务器,消息队列,等等)在同一事务中访问,这样可以使ACID属性跨越应用程序而保持有效.X ...
- 第一篇博客==>Hello_World
1,为什么写博客? 大佬都说程序员需要写博客的说,被无数到的大佬帮我洗脑之后,慢慢也发现了写博客的好处,写博客我认为主要有以下几个作用: 1.打开博客,记录世界记录你.emmm 2.可以把自己的一些经 ...
- 【C/C++开发】ffplay中的FrameQueue的自我理解
最近在研究ffplay,以下是本人今天在研究FrameQueue的时候整理的笔记,如有错误还请有心人指出来~ //这个队列是一个循环队列,windex是指其中的首元素,rindex是指其中的尾部元素. ...
- 关于PADS的一些概念和实用技巧(二)
关于PADS的一些概念和实用技巧(二) 声明:引用请注明出处http://blog.csdn.net/lg1259156776/ 1. 关于制作part 首先在logic中绘制CAE封装,在保存元件时 ...
- linux网卡出现问题:Job for network.service failed because the control process exited with error code问题
[转自]:https://blog.csdn.net/dongfei2033/article/details/81124465 今天在centOS 7下更改完静态ip后发现network服务重启不了, ...
- java输入输出 -- Java NIO之选择器
一.简介 前面的文章说了缓冲区,说了通道,本文就来说说 NIO 中另一个重要的实现,即选择器 Selector.在更早的文章中,我简述了几种 IO 模型.如果大家看过之前的文章,并动手写过代码的话.再 ...