Springboot自动配置原理笔记

Springboot自动配置原理

首先我们先从启动类入手,可以看到有两处值得关注的地方:

  • 注解:@SpringBootApplication
  • run方法:SpringApplication.run()
    Springboot自动配置原理笔记_第1张图片

一、先看下@SpringBootApplication这个注解

Springboot自动配置原理笔记_第2张图片
可以看到上面也有很多注解,这里需要重点了解的注解有以下3个:

  • @SpringBootConfiguration
  • @EnableAutoConfiguration
  • @ComponentScan
    (一)、继续查看源码 @SpringBootConfiguration

Springboot自动配置原理笔记_第3张图片
这里可以看到,在@SpringBootConfiguration这个注解上,又有一个 @Configuration注解。表明声明当前的类是一个配置类,Spring会自动扫描到添加了@Configuration的类,并且读取其中的配置信息。而@SpringBootConfiguration是用来声明当前类是SpringBoot的应用的配置类,项目中只能有一个,我们不需要手动添加。
(二)、@EnableAutoConfiguration
可以看到这个类上有段说明
Springboot自动配置原理笔记_第4张图片
大致的意思就是:启用Spring应用程序上下文的自动配置,尝试猜测和配置您可能需要的bean。比如我们引入了spring-boot-starter-web ,而这个启动器中帮我们添加了tomcat 、SpringMVC的依赖。此时自动配置就知道你是要开发一个web应用,所以就帮你完成了web及SpringMVC的默认配置了!
总结:当使用springboot创建项目,只需引入所需框架的依赖,配置就可以交给springboot处理了。

(三)、@ComponentScan 注解
查看源码可以看到类上的注释:
在这里插入图片描述

  • 大致可以理解为:它的作用类似于标签context:component-scan标签的作用,通过basePackageClasses或者basePackages属性指定要扫描的包。如果没有指定这些属性,那么将从声明这个注解的类所在的包开始,扫描包和子包。
  • @SpringBootApplication注解声明的类就是main函数所在的启动类,因此扫描的包是该类所在包及其子包。所以一般启动类会放在一个比较前的包目录中。

二、默认配置原理

(一)、spring.factories

在SpringApplication类构建的时候,可以看到有这样一段代码
Springboot自动配置原理笔记_第5张图片
点进去
Springboot自动配置原理笔记_第6张图片
可以看到,loadFactoryNames加载了一些FactoryName,然后利用createSpringFactoriesInstances将这些加载到的类名进行实例化。

继续点进loadFactoryNames这个方法,可以看到下面有段通过类加载器加载文件的代码:

public static final String FACTORIES_RESOURCE_LOCATION = "META-INF/spring.factories";

Springboot自动配置原理笔记_第7张图片

可以看到加载的文件地址是:META-INF/spring.factories。ClassLoader默认是从classpath下读取文件的,所以,springboot会在初始化的时候,加载所有classpath:META-INF/spring.factories文件,包括jar包当中的。而在spring的一个依赖包:spring-boot-autoconfigure中,就有这样的文件
Springboot自动配置原理笔记_第8张图片

所以以后我们引入任何第三方启动器,只需要实现自动配置,也都会有类似文件。

(二)、默认配置类

打开刚才的spring.factories文件:
Springboot自动配置原理笔记_第9张图片

可以发现以EnableAutoConfiguration接口为key的一系列配置,key所对应的值,就是所有自动配置类,可以在当前的jar包中找到这些自动配置类:
Springboot自动配置原理笔记_第10张图片

这里看下springMvc的自动配置类:
Springboot自动配置原理笔记_第11张图片

我们可以看下WebMvcAutoConfiguration这个类上的几个注解:

  • @Configuration:声明这是一个配置类
  • @ConditionalOnWebApplication(type =Type.SERVLET):满足项目的类是Type.SERVLET类型,也就是一个普通web工程
  • @ConditionalOnClass({Servlet.class,DispatcherServlet.class,WebMvcConfigurer.class}):满足以下类存在:Servlet、DispatcherServlet、WebMvcConfigurer,其中Servlet只要引入了Tomcat依赖才会有,后两个需要引入SpringMVC才会有。这里就是判断是否引入了相关依赖,引入后条件才会成立,当前配置类才会生效。
  • @ConditionalOnMissingBean(WebMvcConfigurationSupport.class):OnMissingBean,说明环境中没有指定的bean才生效。这就是自定义配置的入口。

再看下WebMvcConfigurationSupport这个类:
视图解析器:
Springboot自动配置原理笔记_第12张图片

处理器适配器(HandlerAdapter):
Springboot自动配置原理笔记_第13张图片

(三)、默认属性配置

配置的属性从哪来?从下图可以看到,在WebMvcAutoConfiguration中,下面通过注解注入了两个属性:WebMvcProperties.class, ResourceProperties.class

分别查看这两个属性类:
WebMvcProperties中找到了内部资源视图解析器的prefix和suffix后缀Springboot自动配置原理笔记_第14张图片

而ResourceProperties中定义了静态资源的路径:
Springboot自动配置原理笔记_第15张图片

用法:如果我们需要覆盖这些属性,只需要在配置文件application.properties中定义与其前缀prefix和字段名一致的属性即可。

三、总结

(一)、使默认配置生效的步骤

  1. @EnableAutoConfiguration注解会去寻找META-INF/spring.factories文件,读取其中以EnableAutoConfiguration为key的所有类的名称,这些类是提前写好的自动配置类。
  2. 这些类都声明了@configuration注解,并且通过@bean注解提前配置了我们需要的一切实例,但是这些配置不一定生效,因为有@ConditionalOn注解,满足一定条件才 会生效。
  3. 类要存在,我们只需要引入相关依赖,依赖有了条件成立,自动配置生效。
  4. 如果我们自己配置了相关bean,那么会覆盖默认的自动配置的bean
  5. 我们还可以通过application.yml文件来覆盖自动配置中的属性。

(二)、启动器

只要引入springboot提供的(stater)启动器,就能自动管理依赖及版本了,所以使用springboot的第一件事就是找启动器。

(三)、全局配置

Springboot的默认配置都会读取默认属性,这些属性可以通过自定义application.properties文件进行覆盖。这样虽然使用的还是默认配置,但是配置中的值已经改成我们自定义的了。
因此,使用springboot的第二件事就是通过配置文件进行覆盖默认的属性值,形成自定义配置。

属性文件支持两种格式:application.yml和application.properties

Yml的语法如下:

jdbc:
 driverClassName: com.mysql.jdbc.Driver
 url: jdbc:mysql://127.0.0.1:3306/springboot_test
 username: root
 password: root
server:
 port: 80

如果两个配置文件都存在且属性重复,则properties优先。

遇到需要修改的组件的配置项流程如下:

Springboot自动配置原理笔记_第16张图片

你可能感兴趣的:(springboot,spring,boot,spring,java)