目錄
1. ConfigurationClassPostProcessor掃描和注冊BeanDefinition
2. 解析配置類 ConfigurationClassParser#parse
???? 2.1 處理內(nèi)部類ConfigurationClassParser#processMemberClasses
???? 2.2 處理@PropertySource注解
???? 2.3 ComponentScanAnnotationParser處理@ComponentScan注解
???? 2.4 處理@Import注解
???? 2.5 處理@ImportResource注解
???? 2.6 處理方法上的@Bean注解
???? 2.7 處理接口的中的default方法
???? 2.8 處理@Import導(dǎo)入的DeferredImportSelector類
3. ConfigurationClassBeanDefinitionReader
???? 3.1 TrackedConditionEvaluator
???? 3.2 注冊Import導(dǎo)入的BeanDefinition
???? 3.3 加載@Bean注解的方法
???? 3.4 加載@ImportResource導(dǎo)入的BeanDefinition
???? 3.5 通過Import導(dǎo)入的ImportBeanDefinitionRegistrar加載BeanDefinition
1. ConfigurationClassPostProcessor掃描和注冊BeanDefinition
在refreshContext()刷新應(yīng)用上下文 invokeBeanFactoryPostProcessors方法中, 執(zhí)行了BeanFactoryPostProcessor#postProcessBeanDefinitionRegistry方法, 其中就包含了ConfigurationClassPostProcessor
主要執(zhí)行了3個步驟
- 首先處理手動注冊的BeanDefinition
- 實例化ConfigurationClassParser, 遞歸掃描@Configuration, @ComponentScan, @Import等注解
- 實例化ConfigurationClassBeanDefinitionReader,遞歸讀取并注冊BeanDefinition
public class ConfigurationClassPostProcessor implements BeanDefinitionRegistryPostProcessor,
PriorityOrdered, ResourceLoaderAware, BeanClassLoaderAware, EnvironmentAware {
//bean定義掃描和注冊
@Override
public void postProcessBeanDefinitionRegistry(BeanDefinitionRegistry registry) {
int registryId = System.identityHashCode(registry);
if (this.registriesPostProcessed.contains(registryId)) {
//this.registriesPostProcessed包含了registryId
//說明postProcessBeanDefinitionRegistry方法已經(jīng)執(zhí)行
throw new IllegalStateException(
"postProcessBeanDefinitionRegistry already called on this post-processor against " + registry);
}
if (this.factoriesPostProcessed.contains(registryId)) {
//this.factoriesPostProcessed已經(jīng)包含了registryId
//說明postProcessBeanFactory方法已經(jīng)執(zhí)行
throw new IllegalStateException(
"postProcessBeanFactory already called on this post-processor against " + registry);
}
//添加到this.registriesPostProcessed中
//標(biāo)記已經(jīng)被執(zhí)行
this.registriesPostProcessed.add(registryId);
//處理bean定義
processConfigBeanDefinitions(registry);
}
//處理bean定義
public void processConfigBeanDefinitions(BeanDefinitionRegistry registry) {
List<BeanDefinitionHolder> configCandidates = new ArrayList<>();
//首先處理手動注冊的BeanDefinition
//獲取手工注冊的bean定義名稱列表
String[] candidateNames = registry.getBeanDefinitionNames();
for (String beanName : candidateNames) {
BeanDefinition beanDef = registry.getBeanDefinition(beanName);
if (ConfigurationClassUtils.isFullConfigurationClass(beanDef) ||
ConfigurationClassUtils.isLiteConfigurationClass(bean)) {
//beanDefinition是lite或者是full
//full指的是使用了Configuration注解
//lite指的是使用了Component, ComponentScan, Import, ImportResource注解
//或者方法包含了Bean注解
if (logger.isDebugEnabled()) {
logger.debug("Bean definition has already been processed as a configuration class: " + beanDef);
}
}
else if (ConfigurationClassUtils.checkConfigurationClassCandidate(beanDef, this.metadataReaderFactory)) {
//當(dāng)前beanDefinition是一個配置類
//添加到configCandidates中
configCandidates.add(new BeanDefinitionHolder(beanDef, beanName));
}
}
if (configCandidates.isEmpty()) {
//如果配置類為空,那么立即返回
return;
}
//@Order注解排序
configCandidates.sort((bd1, bd2) -> {
int i1 = ConfigurationClassUtils.getOrder(bd1.getBeanDefinition());
int i2 = ConfigurationClassUtils.getOrder(bd2.getBeanDefinition());
return Integer.compare(i1, i2);
});
//設(shè)置bean名稱生成策略
SingletonBeanRegistry sbr = null;
if (registry instanceof SingletonBeanRegistry) {
sbr = (SingletonBeanRegistry) registry;
if (!this.localBeanNameGeneratorSet) {
BeanNameGenerator generator = (BeanNameGenerator) sbr.getSingleton(CONFIGURATION_BEAN_NAME_GENERATOR);
if (generator != null) {
this.componentScanBeanNameGenerator = generator;
this.importBeanNameGenerator = generator;
}
}
}
if (this.environment == null) {
this.environment = new StandardEnvironment();
}
//ConfigurationClassParser只負(fù)責(zé)解析被注解的類
//并不進行BeanDefinition的注冊
ConfigurationClassParser parser = new ConfigurationClassParser(
this.metadataReaderFactory, this.problemReporter, this.environment,
this.resourceLoader, this.componentScanBeanNameGenerator, registry);
//Configuration類名
Set<BeanDefinitionHolder> candidates = new LinkedHashSet<>(configCandidates);
//已經(jīng)解析過的ConfigurationClass
Set<ConfigurationClass> alreadyParsed = new HashSet<>(configCandidates.size());
do {
//解析, 維護到parser.configurationClasses中
parser.parse(candidates);
//驗證
//類不可以為final類型, 必須可重寫, static方法不處理
parser.validate();
//configClasses維護待處理的ConfigurationClasse
Set<ConfigurationClass> configClasses = new LinkedHashSet<>(parser.getConfigurationClasses());
configClasses.removeAll(alreadyParsed);
// this.reader初始化為ConfigurationClassBeanDefinitionReader
//進行BeanDefinition的加載
if (this.reader == null) {
this.reader = new ConfigurationClassBeanDefinitionReader(
registry, this.sourceExtractor, this.resourceLoader, this.environment,
this.importBeanNameGenerator, parser.getImportRegistry());
}
//加載BeanDefinition
this.reader.loadBeanDefinitions(configClasses);
//alreadyParsed維護已經(jīng)解析完的class
alreadyParsed.addAll(configClasses);
candidates.clear();
if (registry.getBeanDefinitionCount() > candidateNames.length) {
//說明在加載Configuration注解類的過程中,
//掃描到了Import注解, 引入了新的BeanDefinition
String[] newCandidateNames = registry.getBeanDefinitionNames();
Set<String> oldCandidateNames = new HashSet<>(Arrays.asList(candidateNames));
Set<String> alreadyParsedClasses = new HashSet<>();
for (ConfigurationClass configurationClass : alreadyParsed) {
alreadyParsedClasses.add(configurationClass.getMetadata().getClassName());
}
for (String candidateName : newCandidateNames) {
if (!oldCandidateNames.contains(candidateName)) {
//上次沒有處理過的類
BeanDefinition bd = registry.getBeanDefinition(candidateName);
if (ConfigurationClassUtils.checkConfigurationClassCandidate(bd, this.metadataReaderFactory) &&
!alreadyParsedClasses.contains(bd.getBeanClassName())) {
//@Configuration注解的類
//沒有被處理過
candidates.add(new BeanDefinitionHolder(bd, candidateName));
}
}
}
candidateNames = newCandidateNames;
}
}
//candidates不為空, 說明處理@Configuration注解的類
//掃描到了@Import注解, 引入了新的@Configuration注解類
while (!candidates.isEmpty());
//將@Import引入的類列表注冊為單例Bean
//這樣可以支持Configuration注解的ImportAware的實現(xiàn)類
//在實例化Bean的時候, 可以將Import導(dǎo)入的類, 傳遞給Bean實例
if (sbr != null && !sbr.containsSingleton(IMPORT_REGISTRY_BEAN_NAME)) {
sbr.registerSingleton(IMPORT_REGISTRY_BEAN_NAME, parser.getImportRegistry());
}
if (this.metadataReaderFactory instanceof CachingMetadataReaderFactory) {
//清空緩存
((CachingMetadataReaderFactory) this.metadataReaderFactory).clearCache();
}
}
}
2. 解析配置類 ConfigurationClassParser#parse
ConfigurationClassParser#parse方法, 共執(zhí)行了下面8步
- 處理@Component
- @PropertySources
- @ComponentScans注解的類
- @Import引入的配置類
- @ImportResource導(dǎo)入配置資源類
- 處理@Bean注解
- 處理接口的default方法
- 處理父類
class ConfigurationClassParser {
//解析
//最終都會執(zhí)行processConfigurationClass方法
public void parse(Set<BeanDefinitionHolder> configCandidates) {
for (BeanDefinitionHolder holder : configCandidates) {
BeanDefinition bd = holder.getBeanDefinition();
try {
if (bd instanceof AnnotatedBeanDefinition) {
//AnnotatedBeanDefinition類型
//解析metadata
parse(((AnnotatedBeanDefinition) bd).getMetadata(), holder.getBeanName());
}
else if (bd instanceof AbstractBeanDefinition && ((AbstractBeanDefinition) bd).hasBeanClass()) {
//AbstractBeanDefinition類型
//解析beanClass
parse(((AbstractBeanDefinition) bd).getBeanClass(), holder.getBeanName());
}
else {
//MetadataReader類型
//解析beanClassName
parse(bd.getBeanClassName(), holder.getBeanName());
}
}
catch (BeanDefinitionStoreException ex) {
throw ex;
}
catch (Throwable ex) {
throw new BeanDefinitionStoreException(
"Failed to parse configuration class [" + bd.getBeanClassName() + "]", ex);
}
}
//處理@Import導(dǎo)入的DeferredImportSelectorHolder類
this.deferredImportSelectorHandler.process();
}
//處理@Configuration注解的class
protected void processConfigurationClass(ConfigurationClass configClass) throws IOException {
if (this.conditionEvaluator.shouldSkip(configClass.getMetadata(), ConfigurationPhase.PARSE_CONFIGURATION)) {
return;
}
//判斷是否已經(jīng)被處理過
ConfigurationClass existingClass = this.configurationClasses.get(configClass);
if (existingClass != null) {
//已經(jīng)被處理過了
if (configClass.isImported()) {
//configClass是被Import導(dǎo)入的
if (existingClass.isImported()) {
//將configClass的importedBy合并到existingClass的existingClass中
existingClass.mergeImportedBy(configClass);
}
return;
}
else {
//如果configClass不是被Import導(dǎo)入
//那么說明是一個顯式的bean定義, 我們舊的移除掉
this.configurationClasses.remove(configClass);
this.knownSuperclasses.values().removeIf(configClass::equals);
}
}
SourceClass sourceClass = asSourceClass(configClass);
do {
//遞歸掃描并處理父類, 以及其注解
sourceClass = doProcessConfigurationClass(configClass, sourceClass);
}
while (sourceClass != null);
//維護已經(jīng)處理的類
this.configurationClasses.put(configClass, configClass);
}
//實際解析配置類的方法
@Nullable
protected final SourceClass doProcessConfigurationClass(ConfigurationClass configClass, SourceClass sourceClass)
throws IOException {
//configClass使用了@Component注解
if (configClass.getMetadata().isAnnotated(Component.class.getName())) {
//遞歸處理內(nèi)部類
processMemberClasses(configClass, sourceClass);
}
//處理@PropertySources注解
for (AnnotationAttributes propertySource : AnnotationConfigUtils.attributesForRepeatable(
sourceClass.getMetadata(), @PropertySources.class,
org.springframework.context.annotation.PropertySource.class)) {
if (this.environment instanceof ConfigurableEnvironment) {
//this.environment是ConfigurableEnvironment實例, 才進行@PropertySources屬性替換
processPropertySource(propertySource);
}
else {
logger.info("Ignoring @PropertySource annotation on [" + sourceClass.getMetadata().getClassName() +
"]. Reason: Environment must implement ConfigurableEnvironment");
}
}
// 處理configClass類的@ComponentScans,ComponentScan注解
Set<AnnotationAttributes> componentScans = AnnotationConfigUtils.attributesForRepeatable(
sourceClass.getMetadata(), ComponentScans.class, ComponentScan.class);
if (!componentScans.isEmpty() &&
!this.conditionEvaluator.shouldSkip(sourceClass.getMetadata(), ConfigurationPhase.REGISTER_BEAN)) {
for (AnnotationAttributes componentScan : componentScans) {
// 交付給ComponentScanAnnotationParser進行掃描
Set<BeanDefinitionHolder> scannedBeanDefinitions =
this.componentScanParser.parse(componentScan, sourceClass.getMetadata().getClassName());
for (BeanDefinitionHolder holder : scannedBeanDefinitions) {
//獲取來源Beanthis.reader.loadBeanDefinitions(configClasses)Definition
//OriginatingBeanDefinition由代理設(shè)置
BeanDefinition bdCand = holder.getBeanDefinition().getOriginatingBeanDefinition();
if (bdCand == null) {
bdCand = holder.getBeanDefinition();
}
if (ConfigurationClassUtils.checkConfigurationClassCandidate(bdCand, this.metadataReaderFactory)) {
//BeanDefinition中的類由@Configuration注解
//調(diào)用parse方法, 遞歸處理@Configuration注解的類
parse(bdCand.getBeanClassName(), holder.getBeanName());
}
}
}
}
//處理configClass類的@Import注解
processImports(configClass, sourceClass, getImports(sourceClass), true);
//處理configClass類的@ImportResource注解
AnnotationAttributes importResource =
AnnotationConfigUtils.attributesFor(sourceClass.getMetadata(), ImportResource.class);
if (importResource != null) {
//獲取ImportResource的屬性
String[] resources = importResource.getStringArray("locations");
Class<? extends BeanDefinitionReader> readerClass = importResource.getClass("reader");
for (String resource : resources) {
//處理導(dǎo)入的resource
String resolvedResource = this.environment.resolveRequiredPlaceholders(resource);
configClass.addImportedResource(resolvedResource, readerClass);
}
}
// 處理sourceClass中@Bean注解的方法
Set<MethodMetadata> beanMethods = retrieveBeanMethodMetadata(sourceClass);
for (MethodMetadata methodMetadata : beanMethods) {
//添加到configClass中
configClass.addBeanMethod(new BeanMethod(methodMetadata, configClass));
}
//處理接口中的default方法
processInterfaces(configClass, sourceClass);
// 如果有父類的話, 處理父類
if (sourceClass.getMetadata().hasSuperClass()) {
String superclass = sourceClass.getMetadata().getSuperClassName();
if (superclass != null && !superclass.startsWith("java") &&
!this.knownSuperclasses.containsKey(superclass)) {
this.knownSuperclasses.put(superclass, configClass);
//返回父類
//遞歸處理父類
return sourceClass.getSuperClass();
}
}
//沒有父類, 處理結(jié)束
return null;
}
}
2.1 處理內(nèi)部類ConfigurationClassParser#processMemberClasses
如果內(nèi)部類是full或者lite配置類, 那么就調(diào)用processConfigurationClass方法, 遞歸處理內(nèi)部類, 做內(nèi)部類的處理過程中, 使用了importStack, 維護導(dǎo)入的類, 用于判斷循環(huán)導(dǎo)入
class ConfigurationClassParser {
//處理sourceClass的內(nèi)部類
private void processMemberClasses(ConfigurationClass configClass, SourceClass sourceClass) throws IOException {
Collection<SourceClass> memberClasses = sourceClass.getMemberClasses();
//內(nèi)部類不為空
if (!memberClasses.isEmpty()) {
List<SourceClass> candidates = new ArrayList<>(memberClasses.size());
for (SourceClass memberClass : memberClasses) {
//內(nèi)部類是full或者lite配置類
//也就是使用了@Configuration,@Component或者包含了@Bean方法注解
if (ConfigurationClassUtils.isConfigurationCandidate(memberClass.getMetadata()) &&
!memberClass.getMetadata().getClassName().equals(configClass.getMetadata().getClassName())) {
//維護到candidates列表中
candidates.add(memberClass);
}
}
OrderComparator.sort(candidates);
for (SourceClass candidate : candidates) {
if (this.importStack.contains(configClass)) {
//importStack包含了configClass
//說明出現(xiàn)了循環(huán)導(dǎo)入
this.problemReporter.error(new CircularImportProblem(configClass, this.importStack));
}
else {
this.importStack.push(configClass);
try {
//調(diào)用processConfigurationClass方法, 遞歸處理內(nèi)部類
processConfigurationClass(candidate.asConfigClass(configClass));
}
finally {
//處理完成之后
//將configClass彈出
this.importStack.pop();
}
}
}
}
}
}
2.2 處理@PropertySource注解
讀取@PropertySource注解的各個屬性, 解析locations指定的文件, 然后將屬性維護到environment的propertySources中
class ConfigurationClassParser {
private void processPropertySource(AnnotationAttributes propertySource) throws IOException {
//獲取屬性
String name = propertySource.getString("name");
if (!StringUtils.hasLength(name)) {
name = null;
}
String encoding = propertySource.getString("encoding");
if (!StringUtils.hasLength(encoding)) {
encoding = null;
}
String[] locations = propertySource.getStringArray("value");
Assert.isTrue(locations.length > 0, "At least one @PropertySource(value) location is required");
boolean ignoreResourceNotFound = propertySource.getBoolean("ignoreResourceNotFound");
//自定義PropertySourceFactory類
Class<? extends PropertySourceFactory> factoryClass = propertySource.getClass("factory");
PropertySourceFactory factory = (factoryClass == PropertySourceFactory.class ?
DEFAULT_PROPERTY_SOURCE_FACTORY : BeanUtils.instantiateClass(factoryClass));
for (String location : locations) {
try {
//從配置的location中加載配置數(shù)據(jù)
String resolvedLocation = this.environment.resolveRequiredPlaceholders(location);
Resource resource = this.resourceLoader.getResource(resolvedLocation);
//解析后的數(shù)據(jù)維護到environment的屬性中
addPropertySource(factory.createPropertySource(name, new EncodedResource(resource, encoding)));
}
catch (IllegalArgumentException | FileNotFoundException | UnknownHostException ex) {
if (ignoreResourceNotFound) {
if (logger.isInfoEnabled()) {
logger.info("Properties location [" + location + "] not resolvable: " + ex.getMessage());
}
}
else {
throw ex;
}
}
}
}
//將解析的PropertySource維護到environment的PropertySources中
private void addPropertySource(PropertySource<?> propertySource) {
String name = propertySource.getName();
MutablePropertySources propertySources = ((ConfigurableEnvironment) this.environment).getPropertySources();
if (this.propertySourceNames.contains(name)) {
//this.propertySourceNames包含了屬性
//說明該屬性已經(jīng)被處理過了
//environment的PropertySources中也會有一個對應(yīng)的propertySource
PropertySource<?> existing = propertySources.get(name);
if (existing != null) {
PropertySource<?> newSource = (propertySource instanceof ResourcePropertySource ?
((ResourcePropertySource) propertySource).withResourceName() : propertySource);
//CompositePropertySource組合propertySource的話, 可以維護多個
if (existing instanceof CompositePropertySource) {
//添加到CompositePropertySource列表的首部
((CompositePropertySource) existing).addFirstPropertySource(newSource);
}
else {
if (existing instanceof ResourcePropertySource) {
existing = ((ResourcePropertySource) existing).withResourceName();
}
//轉(zhuǎn)化為組合PropertySource
CompositePropertySource composite = new CompositePropertySource(name);
composite.addPropertySource(newSource);
composite.addPropertySource(existing);
//將原有的替換
propertySources.replace(name, composite);
}
return;
}
}
if (this.propertySourceNames.isEmpty()) {
//添加到propertySources的末尾
propertySources.addLast(propertySource);
}
else {
//添加到上一個propertySource的前面
//順序正好和propertySourceNames相反
String firstProcessed = this.propertySourceNames.get(this.propertySourceNames.size() - 1);
propertySources.addBefore(firstProcessed, propertySource);
}
//維護到propertySourceNames中
//表示已經(jīng)被處理過了
this.propertySourceNames.add(name);
}
}
2.3 ComponentScanAnnotationParser處理@ComponentScan注解
@SpringBootApplication注解使用了@ComponentScan注解
ComponentScanAnnotationParser處理@ComponentScan注解中配置的各個屬性, 然后賦值給ClassPathBeanDefinitionScanner實例, 最后調(diào)用ClassPathBeanDefinitionScanner#doScan方法掃描各個配置類
class ComponentScanAnnotationParser {
public Set<BeanDefinitionHolder> parse(AnnotationAttributes componentScan, final String declaringClass) {
//ClassPathBeanDefinitionScanner負(fù)責(zé)掃描BeanDefi
//useDefaultFilters是否使用默認(rèn)filters
ClassPathBeanDefinitionScanner scanner = new ClassPathBeanDefinitionScanner(this.registry,
componentScan.getBoolean("useDefaultFilters"), this.environment, this.resourceLoader);
//自定義BeanNameGenerator bean名稱生成器
Class<? extends BeanNameGenerator> generatorClass = componentScan.getClass("nameGenerator");
boolean useInheritedGenerator = (BeanNameGenerator.class == generatorClass);
scanner.setBeanNameGenerator(useInheritedGenerator ? this.beanNameGenerator :
BeanUtils.instantiateClass(generatorClass));
//ScopedProxyMode 代理模式
//默認(rèn)不使用代理
//INTERFACES 基于接口, 使用JDK動態(tài)代理
//TARGET_CLASS 基于類, 使用CGLIB代理
ScopedProxyMode scopedProxyMode = componentScan.getEnum("scopedProxy");
if (scopedProxyMode != ScopedProxyMode.DEFAULT) {
scanner.setScopedProxyMode(scopedProxyMode);
}
else {
//scopedProxyMode是DEFAULT
//實例化AnnotationScopeMetadataResolver
Class<? extends ScopeMetadataResolver> resolverClass = componentScan.getClass("scopeResolver");
scanner.setScopeMetadataResolver(BeanUtils.instantiateClass(resolverClass));
}
//設(shè)置resourcePattern
scanner.setResourcePattern(componentScan.getString("resourcePattern"));
for (AnnotationAttributes filter : componentScan.getAnnotationArray("includeFilters")) {
//添加includeFilter
for (TypeFilter typeFilter : typeFiltersFor(filter)) {
scanner.addIncludeFilter(typeFilter);
}
}
for (AnnotationAttributes filter : componentScan.getAnnotationArray("excludeFilters")) {
//添加excludeFilter
for (TypeFilter typeFilter : typeFiltersFor(filter)) {
scanner.addExcludeFilter(typeFilter);
}
}
//配置了laayInit
boolean lazyInit = componentScan.getBoolean("lazyInit");
if (lazyInit) {
scanner.getBeanDefinitionDefaults().setLazyInit(true);
}
//獲取basePackages
Set<String> basePackages = new LinkedHashSet<>();
String[] basePackagesArray = componentScan.getStringArray("basePackages");
for (String pkg : basePackagesArray) {
String[] tokenized = StringUtils.tokenizeToStringArray(this.environment.resolvePlaceholders(pkg),
ConfigurableApplicationContext.CONFIG_LOCATION_DELIMITERS);
Collections.addAll(basePackages, tokenized);
}
for (Class<?> clazz : componentScan.getClassArray("basePackageClasses")) {
basePackages.add(ClassUtils.getPackageName(clazz));
}
if (basePackages.isEmpty()) {
//沒有配置basePackages
//取出declaringClass的包名
basePackages.add(ClassUtils.getPackageName(declaringClass));
}
//設(shè)置忽略自己
scanner.addExcludeFilter(new AbstractTypeHierarchyTraversingFilter(false, false) {
@Override
protected boolean matchClassName(String className) {
return declaringClass.equals(className);
}
});
//掃描basePackages
return scanner.doScan(StringUtils.toStringArray(basePackages));
}
}
ClassPathBeanDefinitionScanner#doScan掃描basePackages
- 調(diào)用父類ClassPathScanningCandidateComponentProvider#findCandidateComponents, 掃描basePackage下的所有注解類, - 調(diào)用AnnotationScopeMetadataResolver#resolveScopeMetadata處理@Scope注解, 然后生成bean名稱
- 設(shè)置BeanDefinition @Autowired注解解析, byType或者byName
- 設(shè)置BeanDefinition通用的注解, Lazy,Primary,DependsOn,Role,Description
- 驗證掃描的類, 驗證通過, 注冊BeanDefinitionHolder, 放入BeanDefinitionHolder中
- 最后返回BeanDefinitionHolder列表
public class ClassPathBeanDefinitionScanner extends ClassPathScanningCandidateComponentProvider {
protected Set<BeanDefinitionHolder> doScan(String... basePackages) {
Assert.notEmpty(basePackages, "At least one base package must be specified");
Set<BeanDefinitionHolder> beanDefinitions = new LinkedHashSet<>();
for (String basePackage : basePackages) {
//調(diào)用父類findCandidateComponents方法
Set<BeanDefinition> candidates = findCandidateComponents(basePackage);
for (BeanDefinition candidate : candidates) {
//獲取candidate BeanDefinition上的Scope注解元數(shù)據(jù)
ScopeMetadata scopeMetadata = this.scopeMetadataResolver.resolveScopeMetadata(candidate);
candidate.setScope(scopeMetadata.getScopeName());
//AnnotationBeanNameGenerator生成bean名稱
//考慮到了cglib動態(tài)代理
String beanName = this.beanNameGenerator.generateBeanName(candidate, this.registry);
if (candidate instanceof AbstractBeanDefinition) {
//設(shè)置@Autowired注解解析 byType或者byName
postProcessBeanDefinition((AbstractBeanDefinition) candidate, beanName);
}
if (candidate instanceof AnnotatedBeanDefinition) {
//設(shè)置通用的注解
//Lazy,Primary,DependsOn,Role,Description
AnnotationConfigUtils.processCommonDefinitionAnnotations((AnnotatedBeanDefinition) candidate);
}
if (checkCandidate(beanName, candidate)) {
//放入BeanDefinitionHolder中
BeanDefinitionHolder definitionHolder = new BeanDefinitionHolder(candidate, beanName);
definitionHolder =
AnnotationConfigUtils.applyScopedProxyMode(scopeMetadata, definitionHolder, this.registry);
//維護到beanDefinitions列表
beanDefinitions.add(definitionHolder);
//注冊definitionHolder
registerBeanDefinition(definitionHolder, this.registry);
}
}
}
return beanDefinitions;
}
}
ClassPathScanningCandidateComponentProvider#findCandidateComponents
掃描basePackage下的所有配置類,通過MetadataReader讀取包中的.class字節(jié)碼, MetadataReader使用了asm框架, 最后處理為一個ScannedGenericBeanDefinition
public class ClassPathScanningCandidateComponentProvider implements EnvironmentCapable, ResourceLoaderAware {
public Set<BeanDefinition> findCandidateComponents(String basePackage) {
if (this.componentsIndex != null && indexSupportsIncludeFilters()) {
//處理META-INF/spring.components配置的Component
return addCandidateComponentsFromIndex(this.componentsIndex, basePackage);
}
else {
//掃描Component
return scanCandidateComponents(basePackage);
}
}
private Set<BeanDefinition> scanCandidateComponents(String basePackage) {
Set<BeanDefinition> candidates = new LinkedHashSet<>();
try {
//獲取包路徑
String packageSearchPath = ResourcePatternResolver.CLASSPATH_ALL_URL_PREFIX +
resolveBasePackage(basePackage) + '/' + this.resourcePattern;
//包內(nèi)的class文件讀取為Resource列表
Resource[] resources = getResourcePatternResolver().getResources(packageSearchPath);
for (Resource resource : resources) {
//處理resource
if (resource.isReadable()) {
try {
//MetadataReader使用了asm框架處理字節(jié)碼
MetadataReader metadataReader = getMetadataReaderFactory().getMetadataReader(resource);
if (isCandidateComponent(metadataReader)) {
//生成ScannedGenericBeanDefinition ScannedGenericBeanDefinition sbd = new ScannedGenericBeanDefinition(metadataReader);
sbd.setResource(resource);
sbd.setSource(resource);
if (isCandidateComponent(sbd)) {
//添加到candidates列表
candidates.add(sbd);
}
//...
return candidates;
}
}
2.4 處理@Import注解
@SpringBootApplication注解使用了@EnableAutoConfiguration注解
- EnableAutoConfiguration注解使用了@Import注解, 導(dǎo)入了AutoConfigurationImportSelector, 找做了兩件事情
- 掃描META-INF/spring-autoconfigure-metadata.properties維護的自動配置組件
- 掃描META-INF/spring.factories中配置的EnableAutoConfiguration子類
- EnableAutoConfiguration使用了@AutoConfigurationPackage注解, 導(dǎo)入了AutoConfigurationPackages.Registrar, 注冊了一個BasePackages類型的Bean
處理@Import注解導(dǎo)入的配置類, 流程如下:
- 如果Import導(dǎo)入的類是否為ImportSelector的子類, 使用反射構(gòu)造導(dǎo)入類的一個實例selector, 先調(diào)用ParserStrategyUtils.invokeAwareMethods方法, 如果實現(xiàn)了Aware接口的話, set相應(yīng)Aware的對象
如果selector是DeferredImportSelector子類, 那么會維護到deferredImportSelectorHandler.deferredImportSelectors列表中, 最后在parse方法最后, 調(diào)用deferredImportSelectorHandler.process()處理selector
selector不是DeferredImportSelector子類, 調(diào)用selector.selectImports方法, 獲取配置類列表, 然后調(diào)用processImports方法, 遞歸處理導(dǎo)入的配置類
- 如果Import導(dǎo)入的類是ImportBeanDefinitionRegistrar的子類, 使用反射構(gòu)造導(dǎo)入類的也實例registrar, 先調(diào)用ParserStrategyUtils.invokeAwareMethods方法, 如果實現(xiàn)了Aware接口的話, set相應(yīng)Aware的對象
ImportBeanDefinitionRegistrar用于動態(tài)注冊BeanDefinition
將registrar添加到configClass.importBeanDefinitionRegistrars列表中
- 如果Import導(dǎo)入的類不是ImportSelector的子類, 也不是ImportBeanDefinitionRegistrar的子類, 就當(dāng)成一個配置類處理
調(diào)用processConfigurationClass方法, 遞歸處理導(dǎo)入的類
class ConfigurationClassParser {
//處理@Import注解
private void processImports(ConfigurationClass configClass, SourceClass currentSourceClass,
Collection<SourceClass> importCandidates, boolean checkForCircularImports) {
//通過getImports方法獲取的class列表
//如果為空,立即返回
if (importCandidates.isEmpty()) {
return;
}
//判斷是否循環(huán)Import
if (checkForCircularImports && isChainedImportOnStack(configClass)) {
this.problemReporter.error(new CircularImportProblem(configClass, this.importStack));
}
else {
//維護到importStack中
this.importStack.push(configClass);
try {
for (SourceClass candidate : importCandidates) {
if (candidate.isAssignable(ImportSelector.class)) {
// ImportSelector子類
Class<?> candidateClass = candidate.loadClass();
//如果是Aware接口的實現(xiàn)類,那么傳入相應(yīng)的生命周期數(shù)據(jù)
ImportSelector selector = BeanUtils.instantiateClass(candidateClass, ImportSelector.class);
ParserStrategyUtils.invokeAwareMethods(
selector, this.environment, this.resourceLoader, this.registry);
if (selector instanceof DeferredImportSelector) {
//DeferredImportSelector子類
//維護到deferredImportSelectorHandler.deferredImportSelectors列表中
this.deferredImportSelectorHandler.handle(
configClass, (DeferredImportSelector) selector);
}
else {
//不是DeferredImportSelector的子類
//調(diào)用selector.selectImports方法, 取出導(dǎo)入的類名
String[] importClassNames = selector.selectImports(currentSourceClass.getMetadata());
Collection<SourceClass> importSourceClasses = asSourceClasses(importClassNames);
//遞歸處理導(dǎo)入的類
processImports(configClass, currentSourceClass, importSourceClasses, false);
}
}
else if (candidate.isAssignable(ImportBeanDefinitionRegistrar.class)) {
// ImportBeanDefinitionRegistrar子類
Class<?> candidateClass = candidate.loadClass();
ImportBeanDefinitionRegistrar registrar =
BeanUtils.instantiateClass(candidateClass, ImportBeanDefinitionRegistrar.class);
ParserStrategyUtils.invokeAwareMethods(
registrar, this.environment, this.resourceLoader, this.registry);
//將registrar添加到configClass.importBeanDefinitionRegistrars列表中
configClass.addImportBeanDefinitionRegistrar(registrar, currentSourceClass.getMetadata());
}
else {
// 不是ImportSelector和ImportBeanDefinitionRegistrar子類, 處理為配置類
this.importStack.registerImport(
currentSourceClass.getMetadata(), candidate.getMetadata().getClassName());
//遞歸處理
processConfigurationClass(candidate.asConfigClass(configClass));
}
}
}
finally {
this.importStack.pop();
}
}
}
//獲取sourceClass配置的@Import注解
private Set<SourceClass> getImports(SourceClass sourceClass) throws IOException {
Set<SourceClass> imports = new LinkedHashSet<>();
Set<SourceClass> visited = new LinkedHashSet<>();
collectImports(sourceClass, imports, visited);
return imports;
}
//收集sourceClass上@Import注解中導(dǎo)入的類
private void collectImports(SourceClass sourceClass, Set<SourceClass> imports, Set<SourceClass> visited)
throws IOException {
//sourceClass維護到visited列表
if (visited.add(sourceClass)) {
for (SourceClass annotation : sourceClass.getAnnotations()) {
String annName = annotation.getMetadata().getClassName();
if (!annName.startsWith("java") && !annName.equals(Import.class.getName())) {
//遞歸收集注解上的@Import注解
collectImports(annotation, imports, visited);
}
}
//獲取@Impost注解的value對應(yīng)的類
//維護到imports列表中
imports.addAll(sourceClass.getAnnotationAttributes(Import.class.getName(), "value"));
}
}
}
2.5 處理@ImportResource注解
讀取xml文件配置, 維護到configClass.importedResources中, key為resource路徑, value為對應(yīng)的reader
2.6 處理方法上的@Bean注解
遍歷sourceClass中@Bean注解的方法, 然后維護到configClass.beanMethods中
class ConfigurationClassParser {
//遍歷@Bean注解的方法
private Set<MethodMetadata> retrieveBeanMethodMetadata(SourceClass sourceClass) {
AnnotationMetadata original = sourceClass.getMetadata();
//獲取@Bean注解的方法
Set<MethodMetadata> beanMethods = original.getAnnotatedMethods(Bean.class.getName());
if (beanMethods.size() > 1 && original instanceof StandardAnnotationMetadata) {
try {
//嘗試使用ASM框架讀取字節(jié)碼
AnnotationMetadata asm =
this.metadataReaderFactory.getMetadataReader(original.getClassName()).getAnnotationMetadata();
Set<MethodMetadata> asmMethods = asm.getAnnotatedMethods(Bean.class.getName());
if (asmMethods.size() >= beanMethods.size()) {
Set<MethodMetadata> selectedMethods = new LinkedHashSet<>(asmMethods.size());
for (MethodMetadata asmMethod : asmMethods) {
//ASM框架讀取的方法順序和JVM加載方法順序不同, 所以使用了雙重for循環(huán)
for (MethodMetadata beanMethod : beanMethods) {
if (beanMethod.getMethodName().equals(asmMethod.getMethodName())) {
//維護到selectedMethods列表中
selectedMethods.add(beanMethod);
break;
}
}
}
if (selectedMethods.size() == beanMethods.size()) {
beanMethods = selectedMethods;
}
}
}
}
return beanMethods;
}
}
2.7 處理接口的中的default方法
遍歷接口的方法, 如果方法不是abstract方法, 那么維護到configClass.beanMethods中
class ConfigurationClassParser {
private void processInterfaces(ConfigurationClass configClass, SourceClass sourceClass) throws IOException {
for (SourceClass ifc : sourceClass.getInterfaces()) {
Set<MethodMetadata> beanMethods = retrieveBeanMethodMetadata(ifc);
for (MethodMetadata methodMetadata : beanMethods) {
if (!methodMetadata.isAbstract()) {
//接口中的非抽象方法
//添加到configClass.beanMethods中
configClass.addBeanMethod(new BeanMethod(methodMetadata, configClass));
}
}
processInterfaces(configClass, ifc);
}
}
}
2.8 處理@Import導(dǎo)入的DeferredImportSelector類
ConfigurationClassParser.parse()方法最后調(diào)用了DeferredImportSelectorHandler#process()方法, 用來處理@Import注解導(dǎo)入的DeferredImportSelector類
class ConfigurationClassParser {
//私有內(nèi)部類DeferredImportSelectorHandler
private class DeferredImportSelectorHandler {
public void process() {
List<DeferredImportSelectorHolder> deferredImports = this.deferredImportSelectors;
//每次調(diào)用都先重置
this.deferredImportSelectors = null;
try {
if (deferredImports != null) {
DeferredImportSelectorGroupingHandler handler = new DeferredImportSelectorGroupingHandler();
deferredImports.sort(DEFERRED_IMPORT_COMPARATOR);
//調(diào)用DeferredImportSelectorGroupingHandler#register方法
//
deferredImports.forEach(handler::register);
handler.processGroupImports();
}
}
finally {
this.deferredImportSelectors = new ArrayList<>();
}
}
}
private class DeferredImportSelectorGroupingHandler {
private final Map<Object, DeferredImportSelectorGrouping> groupings = new LinkedHashMap<>();
private final Map<AnnotationMetadata, ConfigurationClass> configurationClasses = new HashMap<>();
public void register(DeferredImportSelectorHolder deferredImport) {
//獲取importSelector的group
Class<? extends Group> group = deferredImport.getImportSelector()
.getImportGroup();
//實例化一個DeferredImportSelectorGrouping
DeferredImportSelectorGrouping grouping = this.groupings.computeIfAbsent(
(group != null ? group : deferredImport),
key -> new DeferredImportSelectorGrouping(createGroup(group)));
grouping.add(deferredImport);
this.configurationClasses.put(deferredImport.getConfigurationClass().getMetadata(),
deferredImport.getConfigurationClass());
}
//使用group處理import
public void processGroupImports() {
for (DeferredImportSelectorGrouping grouping : this.groupings.values()) {
//grouping.getImports()獲取了Import導(dǎo)入的類
grouping.getImports().forEach(entry -> {
ConfigurationClass configurationClass = this.configurationClasses.get(
entry.getMetadata());
try {
//調(diào)用processImports方法, 遞歸處理Import導(dǎo)入的類
processImports(configurationClass, asSourceClass(configurationClass),
asSourceClasses(entry.getImportClassName()), false);
}
//...
}
}
3. ConfigurationClassBeanDefinitionReader
BeanDefinition讀取器
class ConfigurationClassBeanDefinitionReader {
//加載ConfigurationClass集合對應(yīng)的BeanDefinition
public void loadBeanDefinitions(Set<ConfigurationClass> configurationModel) {
//TrackedConditionEvaluator用于處理@Conditional注解, 記錄結(jié)果, 同時傳入到@Import導(dǎo)入的類中
TrackedConditionEvaluator trackedConditionEvaluator = new TrackedConditionEvaluator();
for (ConfigurationClass configClass : configurationModel) {
//加載ConfigClass對應(yīng)的BeanDefinition
loadBeanDefinitionsForConfigurationClass(configClass, trackedConditionEvaluator);
}
}
//加載ConfigurationClass對應(yīng)的BeanDefinition列表
private void loadBeanDefinitionsForConfigurationClass(
ConfigurationClass configClass, TrackedConditionEvaluator trackedConditionEvaluator) {
if (trackedConditionEvaluator.shouldSkip(configClass)) {
//@Conditional跳過當(dāng)前Bean加載
String beanName = configClass.getBeanName();
if (StringUtils.hasLength(beanName) && this.registry.containsBeanDefinition(beanName)) {
//如果BeanDefinition已經(jīng)被加載過
//移除
this.registry.removeBeanDefinition(beanName);
}
//移除@Import注解導(dǎo)入的BeanDefinition
this.importRegistry.removeImportingClass(configClass.getMetadata().getClassName());
return;
}
if (configClass.isImported()) {
//注冊@Import導(dǎo)入的ConfigurationClass對應(yīng)的BeanDefinition
registerBeanDefinitionForImportedConfigurationClass(configClass);
}
for (BeanMethod beanMethod : configClass.getBeanMethods()) {
//注冊@Bean注解的方法對應(yīng)的BeanDefinition
loadBeanDefinitionsForBeanMethod(beanMethod);
}
//注冊@ImportResource對應(yīng)的BeanDefinition
loadBeanDefinitionsFromImportedResources(configClass.getImportedResources());
//通過Import導(dǎo)入的ImportBeanDefinitionRegistrar加載BeanDefinition
loadBeanDefinitionsFromRegistrars(configClass.getImportBeanDefinitionRegistrars());
}
}
3.1 TrackedConditionEvaluator
擴展了ConditionEvaluator的能力, 記錄了被忽略的ConfigurationClass, 并判斷了導(dǎo)入類是否被忽略,
class ConfigurationClassBeanDefinitionReader {
private class TrackedConditionEvaluator {
//記錄ConfigurationClass類的評估結(jié)果
private final Map<ConfigurationClass, Boolean> skipped = new HashMap<>();
public boolean shouldSkip(ConfigurationClass configClass) {
Boolean skip = this.skipped.get(configClass);
//沒有被評估過
if (skip == null) {
if (configClass.isImported()) {
//導(dǎo)入類
boolean allSkipped = true;
for (ConfigurationClass importedBy : configClass.getImportedBy()) {
if (!shouldSkip(importedBy)) {
//所有的都跳過
allSkipped = false;
break;
}
}
if (allSkipped) {
skip = true;
}
}
if (skip == null) {
//使用conditionEvaluator進行評估
skip = conditionEvaluator.shouldSkip(configClass.getMetadata(), ConfigurationPhase.REGISTER_BEAN);
}
//skipped記錄結(jié)果
this.skipped.put(configClass, skip);
}
return skip;
}
}
}
ConditionEvaluator
條件評估器, 最終調(diào)用Condition接口matches, 進行條件評估
class ConditionEvaluator {
private final ConditionContextImpl context;
public boolean shouldSkip(@Nullable AnnotatedTypeMetadata metadata, @Nullable ConfigurationPhase phase) {
//沒有使用Conditional注解
//那么不跳過
if (metadata == null || !metadata.isAnnotated(Conditional.class.getName())) {
return false;
}
if (phase == null) {
//phase為null
if (metadata instanceof AnnotationMetadata &&
ConfigurationClassUtils.isConfigurationCandidate((AnnotationMetadata) metadata)) {
//@Configuration注解類
return shouldSkip(metadata, ConfigurationPhase.PARSE_CONFIGURATION);
}
return shouldSkip(metadata, ConfigurationPhase.REGISTER_BEAN);
}
List<Condition> conditions = new ArrayList<>();
//取出@Conditional注解value中設(shè)置的class名稱列表
for (String[] conditionClasses : getConditionClasses(metadata)) {
for (String conditionClass : conditionClasses) {
//反射實例化對象
//維護到conditions列表
Condition condition = getCondition(conditionClass, this.context.getClassLoader());
conditions.add(condition);
}
}
AnnotationAwareOrderComparator.sort(conditions);
for (Condition condition : conditions) {
ConfigurationPhase requiredPhase = null;
if (condition instanceof ConfigurationCondition) {
requiredPhase = ((ConfigurationCondition) condition).getConfigurationPhase();
}
//phase符合requiredPhase
//并調(diào)用condition.matches(this.context, metadata)進行驗證
if ((requiredPhase == null || requiredPhase == phase) && !condition.matches(this.context, metadata)) {
return true;
}
}
return false;
}
}
SpringBootCondition
Spring封裝的抽象類, 規(guī)定了matches方法要實現(xiàn)的一些模板方法, 用于打印日志和記錄結(jié)果
public abstract class SpringBootCondition implements Condition {
@Override
public final boolean matches(ConditionContext context,
AnnotatedTypeMetadata metadata) {
String classOrMethodName = getClassOrMethodName(metadata);
try {
ConditionOutcome outcome = getMatchOutcome(context, metadata);
//打印日志
logOutcome(classOrMethodName, outcome);
//記錄評估結(jié)果
recordEvaluation(context, classOrMethodName, outcome);
//返回outcome.match
return outcome.isMatch();
}
//...
}
//抽象方法
//ConditionOutcome記錄了評估結(jié)果和消息
public abstract ConditionOutcome getMatchOutcome(ConditionContext context,
AnnotatedTypeMetadata metadata);
}
3.2 注冊Import導(dǎo)入的BeanDefinition
先獲取configClass的AnnotationMetadata, 然后取出Scope注解, 如果Scope不是DEFAULT或者NO的話, 會生成一個ScopedProxyFactoryBean類型的BeanDefinition, 放入BeanDefinitionHolder中
class ConfigurationClassBeanDefinitionReader {
private void registerBeanDefinitionForImportedConfigurationClass(ConfigurationClass configClass) {
AnnotationMetadata metadata = configClass.getMetadata();
AnnotatedGenericBeanDefinition configBeanDef = new AnnotatedGenericBeanDefinition(metadata);
//取得Scope注解
ScopeMetadata scopeMetadata = scopeMetadataResolver.resolveScopeMetadata(configBeanDef);
configBeanDef.setScope(scopeMetadata.getScopeName());
//生成bean名稱
String configBeanName = this.importBeanNameGenerator.generateBeanName(configBeanDef, this.registry);
//處理通用注解
AnnotationConfigUtils.processCommonDefinitionAnnotations(configBeanDef, metadata);
BeanDefinitionHolder definitionHolder = new BeanDefinitionHolder(configBeanDef, configBeanName);
//如果Scope不是DEFAULT或者NO
//那么就通過ScopedProxyUtils#createScopedProxy生成一個ScopedProxyFactoryBean類型的BeanDefinition
definitionHolder = AnnotationConfigUtils.applyScopedProxyMode(scopeMetadata, definitionHolder, this.registry);
this.registry.registerBeanDefinition(definitionHolder.getBeanName(), definitionHolder.getBeanDefinition());
configClass.setBeanName(configBeanName);
if (logger.isTraceEnabled()) {
logger.trace("Registered bean definition for imported class '" + configBeanName + "'");
}
}
}
3.3 加載@Bean注解的方法
class ConfigurationClassBeanDefinitionReader {
private void loadBeanDefinitionsForBeanMethod(BeanMethod beanMethod) {
ConfigurationClass configClass = beanMethod.getConfigurationClass();
MethodMetadata metadata = beanMethod.getMetadata();
String methodName = metadata.getMethodName();
// 判斷是否要跳過
if (this.conditionEvaluator.shouldSkip(metadata, ConfigurationPhase.REGISTER_BEAN)) {
configClass.skippedBeanMethods.add(methodName);
return;
}
if (configClass.skippedBeanMethods.contains(methodName)) {
return;
}
AnnotationAttributes bean = AnnotationConfigUtils.attributesFor(metadata, Bean.class);
Assert.state(bean != null, "No @Bean annotation attributes");
//獲取@Bean的name屬性
List<String> names = new ArrayList<>(Arrays.asList(bean.getStringArray("name")));
String beanName = (!names.isEmpty() ? names.remove(0) : methodName);
// 注冊alias
for (String alias : names) {
this.registry.registerAlias(beanName, alias);
}
// 是否被重寫
if (isOverriddenByExistingDefinition(beanMethod, beanName)) {
if (beanName.equals(beanMethod.getConfigurationClass().getBeanName())) {
throw new BeanDefinitionStoreException(beanMethod.getConfigurationClass().getResource().getDescription(),
beanName, "Bean name derived from @Bean method '" + beanMethod.getMetadata().getMethodName() +
"' clashes with bean name for containing configuration class; please make those names unique!");
}
return;
}
ConfigurationClassBeanDefinition beanDef = new ConfigurationClassBeanDefinition(configClass, metadata);
beanDef.setResource(configClass.getResource());
beanDef.setSource(this.sourceExtractor.extractSource(metadata, configClass.getResource()));
if (metadata.isStatic()) {
//處理static方法
beanDef.setBeanClassName(configClass.getMetadata().getClassName());
beanDef.setFactoryMethodName(methodName);
}
else {
//處理普通方法
beanDef.setFactoryBeanName(configClass.getBeanName());
//
beanDef.setUniqueFactoryMethodName(methodName);
}
//默認(rèn)使用構(gòu)造器實例化
beanDef.setAutowireMode(AbstractBeanDefinition.AUTOWIRE_CONSTRUCTOR);
//
beanDef.setAttribute(org.springframework.beans.factory.annotation.RequiredAnnotationBeanPostProcessor.
SKIP_REQUIRED_CHECK_ATTRIBUTE, Boolean.TRUE);
AnnotationConfigUtils.processCommonDefinitionAnnotations(beanDef, metadata);
//設(shè)置配置的autowire
Autowire autowire = bean.getEnum("autowire");
if (autowire.isAutowire()) {
beanDef.setAutowireMode(autowire.value());
}
boolean autowireCandidate = bean.getBoolean("autowireCandidate");
if (!autowireCandidate) {
beanDef.setAutowireCandidate(false);
}
//init方法
String initMethodName = bean.getString("initMethod");
if (StringUtils.hasText(initMethodName)) {
beanDef.setInitMethodName(initMethodName);
}
//destory方法
String destroyMethodName = bean.getString("destroyMethod");
beanDef.setDestroyMethodName(destroyMethodName);
//處理Scope注解
ScopedProxyMode proxyMode = ScopedProxyMode.NO;
AnnotationAttributes attributes = AnnotationConfigUtils.attributesFor(metadata, Scope.class);
if (attributes != null) {
beanDef.setScope(attributes.getString("value"));
proxyMode = attributes.getEnum("proxyMode");
if (proxyMode == ScopedProxyMode.DEFAULT) {
proxyMode = ScopedProxyMode.NO;
}
}
//如果Scope不是DEFAULT和NO
//就通過ScopedProxyUtils#createScopedProxy生成一個ScopedProxyFactoryBean類型的BeanDefinition
BeanDefinition beanDefToRegister = beanDef;
if (proxyMode != ScopedProxyMode.NO) {
BeanDefinitionHolder proxyDef = ScopedProxyCreator.createScopedProxy(
new BeanDefinitionHolder(beanDef, beanName), this.registry,
proxyMode == ScopedProxyMode.TARGET_CLASS);
beanDefToRegister = new ConfigurationClassBeanDefinition(
(RootBeanDefinition) proxyDef.getBeanDefinition(), configClass, metadata);
}
if (logger.isTraceEnabled()) {
logger.trace(String.format("Registering bean definition for @Bean method %s.%s()",
configClass.getMetadata().getClassName(), beanName));
}
//注冊BeanDefinition
this.registry.registerBeanDefinition(beanName, beanDefToRegister);
}
}
3.4 加載@ImportResource導(dǎo)入的BeanDefinition
通過BeanDefinitionReader加載BeanDefinition
3.5 通過Import導(dǎo)入的ImportBeanDefinitionRegistrar加載BeanDefinition
通過執(zhí)行的ImportBeanDefinitionRegistrar子類的registerBeanDefinitions方法, 加載BeanDefinition