spring-boot 自动装配

1
2
3
4
5
6
@SpringBootApplication
public class DemoApplication {
public static void main(String[] args) {
ConfigurableApplicationContext context = SpringApplication.run(DemoApplication.class, args);
}
}

通过 SpringApplication.run 可以进入方法得知 spring 底层自动扫描所有在META-INF/spring.factories中默认配置好的自动装配类,然后根据条件按需加载组件(bean)到 spring 容器中。

1
2
3
4
5
6
7
8
9

private static Map<String, List<String>> loadSpringFactories(@Nullable ClassLoader classLoader) {

try {
Enumeration<URL> urls = (classLoader != null ?
classLoader.getResources(FACTORIES_RESOURCE_LOCATION) :
ClassLoader.getSystemResources(FACTORIES_RESOURCE_LOCATION));
}
}
1
2
3
4
5
6
7
8
9
package cc.voox.demo;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.ConfigurableApplicationContext;

@SpringBootApplication
public class DemoApplication {
}

@SpringBootApplication 是由多个注解组合而成。

1
2
3
4
5
6
@SpringBootConfiguration
@EnableAutoConfiguration
@ComponentScan(excludeFilters = { @Filter(type = FilterType.CUSTOM, classes = TypeExcludeFilter.class),
@Filter(type = FilterType.CUSTOM, classes = AutoConfigurationExcludeFilter.class) })
public @interface SpringBootApplication {
}

@SpringBootConfiguration 和@Configuration 功能一样

1
2
@Configuration
public @interface SpringBootConfiguration {}

@SpringBootConfiguration is a class-level annotation that is part of the Spring Boot framework. It indicates that a class provides application configuration. Spring Boot favors Java-based configuration. As a result, the @SpringBootConfiguration annotation is the primary source for configuration in applications.

@ComponentScan 包扫描器

1
2
3
4
@AutoConfigurationPackage
@Import(AutoConfigurationImportSelector.class)
public @interface EnableAutoConfiguration {
}

自动导入AutoConfigurationImportSelector 组件后,通过selectImports方法封装所有满足的类成AutoConfigurationEntry进行导入
image.png

1
2
3
4
5
6
@Override
public String[] selectImports(AnnotationMetadata annotationMetadata) {

AutoConfigurationEntry autoConfigurationEntry = getAutoConfigurationEntry(annotationMetadata);
return StringUtils.toStringArray(autoConfigurationEntry.getConfigurations());
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
protected AutoConfigurationEntry getAutoConfigurationEntry(AnnotationMetadata annotationMetadata) {
if (!isEnabled(annotationMetadata)) {
return EMPTY_ENTRY;
}
AnnotationAttributes attributes = getAttributes(annotationMetadata);
List<String> configurations = getCandidateConfigurations(annotationMetadata, attributes);
configurations = removeDuplicates(configurations);
Set<String> exclusions = getExclusions(annotationMetadata, attributes);
checkExcludedClasses(configurations, exclusions);
configurations.removeAll(exclusions);
configurations = getConfigurationClassFilter().filter(configurations);
fireAutoConfigurationImportEvents(configurations, exclusions);
return new AutoConfigurationEntry(configurations, exclusions);
}

利用PackageImports类批量注册组件到容器中。

1
2
3
4
5
6
7
8
9
10
11
12

@Import(AutoConfigurationPackages.Registrar.class)
public @interface AutoConfigurationPackage {
}

static class Registrar implements ImportBeanDefinitionRegistrar, DeterminableImports {

@Override
public void registerBeanDefinitions(AnnotationMetadata metadata, BeanDefinitionRegistry registry) {
register(registry, new PackageImports(metadata).getPackageNames().toArray(new String[0]));
}
}

本博客所有文章除特别声明外,均采用 CC BY-SA 4.0 协议 ,转载请注明出处!