您现在的位置是:首页 >学无止境 >Spring Boot自动装配网站首页学无止境
Spring Boot自动装配
简介Spring Boot自动装配
目录
点击进入@EnableAutoConfiguration注解
AutoConfigurationImportSelector(核心)
点进getAutoConfigurationEntry()方法:
点进getCandidateConfigurations()
是什么?
Spring Boot自动装配(Automatic Configuration)是指Spring Boot框架中的一种特性,它可以根据应用程序中的依赖关系和配置来自动配置Spring应用程序的各个部分。在Spring Boot中,自动装配通过使用条件化的配置和智能配置来实现(如:condition),这样可以根据应用程序的环境和需要来自动配置不同的组件,例如spring-boot-starter-redis等。自动装配能够大大减少Spring应用程序的配置量,并且使得应用程序更易于维护和升级。
自动装配的原理
进入@SpringBootApplication注解
其中通过@EnableAutoConfiguration注解实现了自动装配。
@Target({ElementType.TYPE}) // 该注解作用于接口、类、枚举
@Retention(RetentionPolicy.RUNTIME) // 注解不仅被保存到class文件中,jvm加载class文件之后,仍然存在
@Documented // 有了该注释后,如果有接口使用了该注解,生成的javadoc文件中,会把该注解展示出来
@Inherited // 如果一个类用上了@Inherited修饰的注解,那么其子类也会继承这个注解
@SpringBootConfiguration // 标识它是一个Spring Boot配置类
@EnableAutoConfiguration // 主要是通过这个注解实现自动装配
@ComponentScan( // 配置类上添加 @ComponentScan 注解。该注解默认会扫描该类所在的包下所有的配置类
excludeFilters = {@Filter(
type = FilterType.CUSTOM,
classes = {TypeExcludeFilter.class}
), @Filter(
type = FilterType.CUSTOM,
classes = {AutoConfigurationExcludeFilter.class}
)})
public @interface SpringBootApplication {
。。。
}
点击进入@EnableAutoConfiguration注解
@Target({ElementType.TYPE}) // 该注解作用于接口、类、枚举
@Retention(RetentionPolicy.RUNTIME) // 注解不仅被保存到class文件中,jvm加载class文件之后,仍然存在
@Documented // 有了该注释后,如果有接口使用了该注解,生成的javadoc文件中,会把该注解展示出来
@Inherited // 如果一个类用上了@Inherited修饰的注解,那么其子类也会继承这个注解
@AutoConfigurationPackage // 记录使用了该注释的类所在的包以及子包的路径,以便后序读取
@Import({AutoConfigurationImportSelector.class})
public @interface EnableAutoConfiguration{...}
AutoConfigurationImportSelector(核心)
@Override
public String[] selectImports(AnnotationMetadata annotationMetadata) {
if (!isEnabled(annotationMetadata)) {
return NO_IMPORTS;
}
AutoConfigurationEntry autoConfigurationEntry = getAutoConfigurationEntry(annotationMetadata);
return StringUtils.toStringArray(autoConfigurationEntry.getConfigurations());
}
点进getAutoConfigurationEntry()方法:
protected AutoConfigurationEntry getAutoConfigurationEntry(AnnotationMetadata annotationMetadata) {
if (!isEnabled(annotationMetadata)) {
return EMPTY_ENTRY;
}
//@EnableAutoConfiguration中的exclude、excludeName等
AnnotationAttributes attributes = getAttributes(annotationMetadata);
//获取所有自动装配的配置类,也就是读取spring.factories文件
List<String> configurations = getCandidateConfigurations(annotationMetadata, attributes);
//去除重复的配置项。
configurations = removeDuplicates(configurations);
//根据@EnableAutoConfiguration中的exclude、excludeName移除不需要的配置类。
Set<String> exclusions = getExclusions(annotationMetadata, attributes);
checkExcludedClasses(configurations, exclusions);
configurations.removeAll(exclusions);
configurations = getConfigurationClassFilter().filter(configurations);
//广播事件
fireAutoConfigurationImportEvents(configurations, exclusions);
return new AutoConfigurationEntry(configurations, exclusions);
}
- getAttributes获取@EnableAutoConfiguration中的exclude、excludeName等。
- getCandidateConfigurations获取所有自动装配的配置类,也就是读取spring.factories文件,后面会再次说明。
- removeDuplicates去除重复的配置项。
- getExclusions根据@EnableAutoConfiguration中的exclude、excludeName移除不需要的配置类。
- fireAutoConfigurationImportEvents 广播事件
点进getCandidateConfigurations()
这里通过loadFactoryNames方法,扫描classpath下的META-INF/spring.factories文件,里面是以key=value形式存储,我们读取其中key=EnableAutoConfiguration,value就是需要装配的配置类,也就是getCandidateConfigurations返回的值。
protected List<String> getCandidateConfigurations(AnnotationMetadata metadata, AnnotationAttributes attributes) {
List<String> configurations = SpringFactoriesLoader.loadFactoryNames(this.getSpringFactoriesLoaderFactoryClass(), this.getBeanClassLoader());
Assert.notEmpty(configurations, "No auto configuration classes found in META-INF/spring.factories. If you are using a custom packaging, make sure that file is correct.");
return configurations;
}
流程图
风语者!平时喜欢研究各种技术,目前在从事后端开发工作,热爱生活、热爱工作。