SpringBoot实现自动化配置与@SpringBootApplication启动注解的作用密不可分。首先进入@SpringBootApplication注解源码中,发现有三个注解@SpringBootConfiguration、@EnableAutoConfiguration、@ComponentScan,这三个注解可以替代@SpringBootApplication启动。接下来从这三个注解开始分析。
其中@SpringBootConfiguration和@ComponentScan的作用较为简单
作用:
@SpringBootConfiguration:点进源码发现其实底层就是个@Configuration注解,相当于xml的头文件,会在Spring容器初始化的过程中扫描加载。
@ComponentScan:这个注解的作用是扫描当前所在包和所在包的子包,相当于xml文件配置中
<context:component-scan base-package="com.tpa"/>
这也是为什么我们通常把启动类放在rootpackage下。
@EnableAutoConfiguration这个注解是SpringBoot实现自动化配置的灵魂。他也是一个派生注解。
关键功能是由@Import注解导入的AutoConfigurationImportSelector类所提供的。接下来进入AutoConfigurationImportSelector中进行DEBUG。
DEBUG进入到AutoConfigurationImportSelector的selectImports方法中,在这个方法中调用了getCandidateConfigurations方法,继续进入此方法查看
在getCandidateConfigurations方法中调用了SpringFactoriesLoader.loadFactoryNames 方法,该方法的作用就是从META-INF/spring.factories文件中读取指定类对应的类名称列表在这个方法出错时,会显示 No auto configuration classes found in META-INF/spring.factories. If you are using a custom packaging, make sure that file is correct.这段话
在SpringFactoriesLoader类中
接着找到org.springframework.boot.autoconfigure/META-INF/spring.factories文件,打开这个文件我们可以看到,spring.factories 文件中有关自动配置的配置信息
在其中看见了很多熟悉的名字,以ServletWebServerFactoryAutoConfiguration为例 ,点进源码看看
查看发现有@ConditionalOnClass这个注解
每一个XxxxAutoConfiguration自动配置类都是在某些条件之下才会生效的,这些条件的限制在Spring Boot中以注解的形式体现,常见的条件注解有如下几项:
@ConditionalOnBean:当容器里有指定的bean的条件下。
@ConditionalOnMissingBean:当容器里不存在指定bean的条件下。
@ConditionalOnClass:当类路径下有指定类的条件下。
@ConditionalOnMissingClass:当类路径下不存在指定类的条件下。
那么全局配置文件又是如何生效的呢
ServletWebServerFactoryAutoConfiguration类上,有一个@EnableConfigurationProperties
注解:开启配置属性,而它后面的参数是一个ServerProperties类,这就是习惯优于配置的最终落地点。
进入ServerProperties查看,我们看见了很多常见的属性,除此之外还有个非常熟悉的注解:@ConfigurationProperties,它的作用就是从配置文件中绑定属性到对应的bean上,而@EnableConfigurationProperties负责导入这个已经绑定了属性的bean到spring容器中。
那么所有其他的和这个类相关的属性都可以在全局配置文件中定义,也就是说,真正“限制”我们可以在全局配置文件中配置哪些属性的类就是这些XxxxProperties类,它与配置文件中定义的prefix关键字开头的一组属性是唯一对应的。
至此,我们大致可以了解。在全局配置的属性如:server.port等,通过@ConfigurationProperties注解,绑定到对应的XxxxProperties配置实体类上封装为一个bean,然后再通过@EnableConfigurationProperties注解导入到Spring容器中。
而诸多的XxxxAutoConfiguration自动配置类,就是Spring容器的JavaConfig形式,作用就是为Spring 容器导入bean,而所有导入的bean所需要的属性都通过xxxxProperties的bean来获得。