SpringBoot原理发现(二)
说明:
本系列基于SpringBoot 2.2.9.RELEASE 版本,对SpringBoot的原理进行分析,一共分为四节:
SpringBoot原理发现(一):创建Hello World,对pom依赖以及@SpringBootApplication注解进行分析
SpringBoot原理发现(二):分析SpringBoot自动配置原理
SpringBoot原理发现(三):通过主配置类main方法分析SpringBoot启动配置原理
SpringBoot原理发现(四):了解SpringBoot启动中的几个重要回调机制
自动配置原理
1. 自动配置源头
@EnableAutoConfiguration
@Target(ElementType.TYPE) @Retention(RetentionPolicy.RUNTIME) @Documented @Inherited @SpringBootConfiguration @EnableAutoConfiguration @ComponentScan(excludeFilters = { @Filter(type = FilterType.CUSTOM, classes = TypeExcludeFilter.class), @Filter(type = FilterType.CUSTOM, classes = AutoConfigurationExcludeFilter.class) }) public @interface SpringBootApplication {
通过 SpringBoot原理发现(一)可以得出:
1)SpringBoot启动的时候加载主配置类,通过@EnableAutoConfiguration开启了自动配置功能。
2)@EnableAutoConfiguration的作用:
A. @AutoConfigurationPackage:自动配置包,扫描主配置类所在包路径下面的所有组件并初始化进容器
B. @Import(AutoConfigurationImportSelector.class) :通过源码,可以看出它是去扫描所有jar包类路径下面的 META-INF/Spring.factories,并返回EnableAutoConfiguration.class指定的值列表,并添加至容器中,如下图:
# Auto Configure org.springframework.boot.autoconfigure.EnableAutoConfiguration=\ org.springframework.boot.autoconfigure.admin.SpringApplicationAdminJmxAutoConfiguration,\ org.springframework.boot.autoconfigure.aop.AopAutoConfiguration,\ org.springframework.boot.autoconfigure.amqp.RabbitAutoConfiguration,\ org.springframework.boot.autoconfigure.batch.BatchAutoConfiguration,\ org.springframework.boot.autoconfigure.cache.CacheAutoConfiguration,\ org.springframework.boot.autoconfigure.cassandra.CassandraAutoConfiguration,\ org.springframework.boot.autoconfigure.cloud.CloudServiceConnectorsAutoConfiguration,\ org.springframework.boot.autoconfigure.context.ConfigurationPropertiesAutoConfiguration,\ org.springframework.boot.autoconfigure.context.MessageSourceAutoConfiguration,\ org.springframework.boot.autoconfigure.context.PropertyPlaceholderAutoConfiguration,\ org.springframework.boot.autoconfigure.couchbase.CouchbaseAutoConfiguration,\ ......
上面的每一个XXXAutoConfiguration就是一个组件,它们的作用就是进行自动配置功能。
2. 配置文件配置属性
打开spring-boot-autoconfigure-2.2.9.RELEASE.jar/META-INF/spring.factories文件,找到其中的EnableAutoConfiguration类指定的值,以HttpEncodingAutoConfiguration为例
@Configuration(proxyBeanMethods = false) @EnableConfigurationProperties(HttpProperties.class) @ConditionalOnWebApplication(type = ConditionalOnWebApplication.Type.SERVLET) @ConditionalOnClass(CharacterEncodingFilter.class) @ConditionalOnProperty(prefix = "spring.http.encoding", value = "enabled", matchIfMissing = true) public class HttpEncodingAutoConfiguration {
其他注解略过..
2.1 @EnableConfigurationProperties(HttpProperties.class)
开启HttpProperties.class)的配置属性功能,进入HttpProperties,可以看到如下代码:
@ConfigurationProperties(prefix = "spring.http") public class HttpProperties {
@ConfigurationProperties(prefix = "spring.http"):该注解是从配置文件中获取spring.http的值和Bean的属性进行绑定。
而有哪些属性可配置在配置文件中就可以参考当前Bean拥有的属性。
yml文件:
spring:
http:
encoding:
charset: gbk
通过debug如下代码:
@SpringBootApplication public class DemoApplication { @Autowired private CharacterEncodingFilter characterEncodingFilter; public static void main(String[] args) { SpringApplication.run(DemoApplication.class, args); }
/** * HttpEncodingAutoConfiguration.class */ @Bean @ConditionalOnMissingBean public CharacterEncodingFilter characterEncodingFilter() { CharacterEncodingFilter filter = new OrderedCharacterEncodingFilter(); filter.setEncoding(this.properties.getCharset().name()); filter.setForceRequestEncoding(this.properties.shouldForce(Type.REQUEST)); filter.setForceResponseEncoding(this.properties.shouldForce(Type.RESPONSE)); return filter; }
yaml文件中设置的GBK,自动和HttpProperties的属性进行了绑定
所以配置文件中能配置哪些属性,就可以查看XXXProperties类的属性进行配置。
观察其他的XXXAutoConfiguration,如:RedisAutoConfiguration , CacheAutoConfiguration
都能发现 @EnableConfigurationProperties(XXXProperties.class)
@Configuration(proxyBeanMethods = false) @ConditionalOnClass(RedisOperations.class) @EnableConfigurationProperties(RedisProperties.class) @Import({ LettuceConnectionConfiguration.class, JedisConnectionConfiguration.class }) public class RedisAutoConfiguration {
可以发现,SpringBoot有很多这种模式: