其他阶段的解析参考:
总体概括
实例化阶段主要涉及到两部分:
第一部分,
BeanPostProcessor的注册
按源码中的顺序将后置处理器注册到容器中,因为后置处理器在bean生命周期中作用重大,需要先进行注册
第二部分,Bean 的实例化
第一步,先合并Bean定义(后面还有一次),这里合并的是通过解析配置类得到的Bean定义。然后通过Bean定义对非抽象的、非延迟加载的、单实例的bean进行实例化
第二步,区分工厂Bean与普通Bean,二者处理不同:
-
工厂bean默认懒加载,除非设置为立刻初始化才会创建bean(即
isEagerInit = true); -
普通bean则会直接创建
第三步,创建bean实例,如果是普通Bean或设置为立刻初始化的工厂Bean,则执行getBean方法进行创建,其核心过程为:
- 再次合并
BeanDefinition(之前合并过一次,这次合并会先从缓存获取),合并的核心逻辑是自下而上递归寻找父BeanDefinition,再从上到下覆盖合并获得最终的BeanDefinition - 通过合并后的
BeanDefinition对单实例 bean 和原型 bean 进行不同的处理(虽然源码是处理这两种,但实际容器启动进入刷新方法后只会对单实例bean做处理),代码在doGetBean方法中:- 原型bean直接执行
createBean方法进行bean创建。注意:第一步既然已经限定了处理单实例bean,这还有原型bean处理的原因是,doGetBean方法是通用设计的,会涉及其他场景的调用,所以没有去掉原型bean处理 - 单实例bean使用了一个
ObjectFactory来进行bean创建,原因是单实例 bean 只能创建一次,再次获取时需要从缓存中拿出,如果在创建单例bean时缓存中没有,则使用ObjectFactory来执行createBean方法进行bean创建
- 原型bean直接执行
第四步,调用 InstantiationAwareBeanPostProcessor 的 postProcessBeforeInstantiation 方法,作用是给后置处理器一个机会来创建代理 bean 而不是目标 bean 实例。如果成功创建,则会直接调用 postProcessAfterInitialization 方法初始化 bean 后返回。
第五步,执行createBean方法进行bean创建,也就是实例化,其方法内核心步骤如下,按顺序依次执行判断,那个满足就用哪个创建:
- 如果bean定义中的设置了自定义的实例化方法Supplier,则使用此方法进行bean的实例化
- 如果bean定义中有指定工厂方法,则反射调用工厂方法来进行bean的实例化
- 使用后置处理器获取构造方法,如果有获取到构造方法,则通过构造方法进行Bean的实例化,当存在构造方法的依赖注入时,还会执行相关的注入
- 如果上面三个都不满足,则反射调用无参构造函数兜底创建
源码位置
源码版本:
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.7.10</version>
</parent>
主启动类run方法中进行刷新:

上图红框处的刷新方法触发进入到
AbstractApplicationContext的refresh()方法:
refresh()中的registerBeanPostProcessors就是用来注册Bean后置处理器BeanPostProcessor的:

而在
refresh()方法体内的下方还有一个finishBeanFactoryInitialization方法,此方法包含bean的实例化、属性注入、初始化三个步骤,Bean的实例化操作就包含在其中:

下面结合源码介绍Bean的实例化阶段
1.注册BeanPostProcessor
第一步是注册
BeanPostProcessor,即Bean后置处理器。进入refresh方法内的registerBeanPostProcessors中:
protected void registerBeanPostProcessors(ConfigurableListableBeanFactory beanFactory) {
// 代理调用`registerBeanPostProcessors`方法进行注册
PostProcessorRegistrationDelegate.registerBeanPostProcessors(beanFactory, this);
}
又是走了代理的方法,进入
registerBeanPostProcessors中查看:
此代理方法的核心在于BeanPostProcessor的注册顺序管理。Spring必须严格遵循PriorityOrdered、Ordered和无序处理器的注册顺序,否则会导致循环依赖或初始化顺序错误。
public static void registerBeanPostProcessors(
ConfigurableListableBeanFactory beanFactory, AbstractApplicationContext applicationContext) {
// 获取容器中所有 BeanPostProcessor 类型的Bean名称,包括非单例Bean,但不会初始化这些bean
String[] postProcessorNames = beanFactory.getBeanNamesForType(BeanPostProcessor.class, true, false);
// 此处会先注册一个BeanPostProcessorChecker
// 作用:如果在在`BeanPostProcessor`实例化期间有Bean创建,则记录日志信息
int beanProcessorTargetCount = beanFactory.getBeanPostProcessorCount() + 1 + postProcessorNames.length;
beanFactory.addBeanPostProcessor(new BeanPostProcessorChecker(beanFactory, beanProcessorTargetCount));
// 下面是创建存放不同类型后置处理器的集合,用于区分处理(注意:两个集合存处理器,两个集合存bean名称):
// 该集合存储实现了`PriorityOrdered`的后置处理器,该类型处理器有最高处理优先级
List<BeanPostProcessor> priorityOrderedPostProcessors = new ArrayList<>();
// 该集合存储`MergedBeanDefinitionPostProcessor`类型后置处理器,该类型需要特殊处理
List<BeanPostProcessor> internalPostProcessors = new ArrayList<>();
// 该集合存储实现了`Ordered`的后置处理器的Bean名称,该类型处理器有中等处理优先级,在`PriorityOrdered`之后处理
List<String> orderedPostProcessorNames = new ArrayList<>();
// 该集合存储普通后置处理器的Bean名称,该类型处理器优先级最低,在`Ordered`之后处理
List<String> nonOrderedPostProcessorNames = new ArrayList<>();
// 遍历后置处理器的bean名
for (String ppName : postProcessorNames) {
// 这里通过bean名,获取`PriorityOrdered`类型的后置处理器
if (beanFactory.isTypeMatch(ppName, PriorityOrdered.class)) {
// 这里是获取bean,此处代码一执行,PriorityOrdered类型的后置处理器就被初始化了,它是最先初始化
BeanPostProcessor pp = beanFactory.getBean(ppName, BeanPostProcessor.class);
// 将该类型处理器添加到集合中
priorityOrderedPostProcessors.add(pp);
// `MergedBeanDefinitionPostProcessor`类型的处理器要额外筛出来,后面做特殊处理
if (pp instanceof MergedBeanDefinitionPostProcessor) {
// 将`MergedBeanDefinitionPostProcessor`类型处理器的添加到`internalPostProcessors`集合中
internalPostProcessors.add(pp);
}
}
// 通过bean名判断当前bean是不是`Ordered`类型的后置处理器
else if (beanFactory.isTypeMatch(ppName, Ordered.class)) {
// 如果是则将bean名称添加到对应集合中,这里就没有用getBean初始化`Ordered`类型的后置处理器
orderedPostProcessorNames.add(ppName);
}
// 通过bean名断当前bean是不是普通的后置处理器
else {
// 如果是则将bean名称添加到对应集合中,这里也没有用getBean初始化普通的后置处理器
nonOrderedPostProcessorNames.add(ppName);
}
}
// 第一步,先对所有实现了`PriorityOrdered`接口的后置处理器进行排序
sortPostProcessors(priorityOrderedPostProcessors, beanFactory);
// 注册所有实现了`PriorityOrdered`接口的后置处理器
// 此处会将这些处理器存放到`AbstractBeanFactory`的`beanPostProcessors`集合属性中
registerBeanPostProcessors(beanFactory, priorityOrderedPostProcessors);
// 第二步,注册所有实现了`Ordered`接口的后置处理器
// 创建一个存放`Ordered`类型的后置处理器的集合,注意这里不是存bean名了,而是存处理器了
List<BeanPostProcessor> orderedPostProcessors = new ArrayList<>(orderedPostProcessorNames.size());
// 遍历所有`Ordered`类型的后置处理器的bean名
for (String ppName : orderedPostProcessorNames) {
// 这里初始化`Ordered`类型的后置处理器
BeanPostProcessor pp = beanFactory.getBean(ppName, BeanPostProcessor.class);
// 将`Ordered`类型的后置处理器存入上面的集合中
orderedPostProcessors.add(pp);
// 再次把`MergedBeanDefinitionPostProcessor`类型的处理器筛出来,后面做特殊处理
if (pp instanceof MergedBeanDefinitionPostProcessor) {
// 把当前处理器存入`MergedBeanDefinitionPostProcessor`类型的后置处理器集合
internalPostProcessors.add(pp);
}
}
// 对所有实现了`Ordered`接口的后置处理器进行排序
sortPostProcessors(orderedPostProcessors, beanFactory);
// 注册所有实现了`Ordered`接口的后置处理器,依然是存到`AbstractBeanFactory`的`beanPostProcessors`集合中
registerBeanPostProcessors(beanFactory, orderedPostProcessors);
// 第三步,注册所有普通的后置处理器
// 创建一个存放普通后置处理器的集合,注意这里不是存bean名了,而是存处理器了
List<BeanPostProcessor> nonOrderedPostProcessors = new ArrayList<>(nonOrderedPostProcessorNames.size());
// 遍历所有普通后置处理器的bean名
for (String ppName : nonOrderedPostProcessorNames) {
// 初始化普通的后置处理器
BeanPostProcessor pp = beanFactory.getBean(ppName, BeanPostProcessor.class);
// 添加到上面集合中
nonOrderedPostProcessors.add(pp);
// 继续收集`MergedBeanDefinitionPostProcessor`类型的后置处理器
if (pp instanceof MergedBeanDefinitionPostProcessor) {
internalPostProcessors.add(pp);
}
}
// 普通处理器没有顺序要求,这里直接注册。也依然是存到`AbstractBeanFactory`的`beanPostProcessors`集合中
registerBeanPostProcessors(beanFactory, nonOrderedPostProcessors);
// 第四步,处理`MergedBeanDefinitionPostProcessor`类型的后置处理器
// 先排序
sortPostProcessors(internalPostProcessors, beanFactory);
// 注册`MergedBeanDefinitionPostProcessor`类型的后置处理器
// 这里相当于是再次注册,因为在上面它们作为`PriorityOrdered`或`Ordered`已经被注册过一次
registerBeanPostProcessors(beanFactory, internalPostProcessors);
// 最后又注册了一个ApplicationListenerDetector,该后置处理器用来注册监听器
beanFactory.addBeanPostProcessor(new ApplicationListenerDetector(applicationContext));
}
理一下这个方法的整体逻辑脉络:
-
首先它会先获取到 IOC 容器中已经有的
BeanPostProcessor的name,获取到之后先不处理 -
注册一个
BeanPostProcessorChecker,它的作用是:-
检查
BeanPostProcessor的初始化阶段中是否有注入其他的普通bean。如果有则记录警告日志,形如:Bean 'xxx' of type ["xxx"] is not eligible for getting processed by all BeanPostProcessors (for example: not eligible for auto-proxying) -
需要此检查的原因: 普通 Bean 在初始化时,若某些
BeanPostProcessor(如AbstractAutoProxyCreator)未就绪,此Bean将无法被完整处理(如未被代理)
-
-
在其他的
BeanPostProcessor注册之前,先初始化并注册实现了PriorityOrdered接口的后置处理器,原因是:- 实现了
PriorityOrdered接口的组件通常都是些优先级较高的内置的核心组件,SpringFramework 为了保证功能的正常运转,就必须要让这些核心组件都正常到位才可以,因此它们有最高优先级。 - 比如:用于处理
@Autowired注解的AutowiredAnnotationBeanPostProcessor,处理 JSR250 规范注解的CommonAnnotationBeanPostProcessor
- 实现了
-
注册所有实现了
Ordered接口的后置处理器 -
注册所有普通后置处理器
-
注册所有
MergedBeanDefinitionPostProcessor类型的后置处理器。这里相当于是重新注册,因为这些处理器在前面已经作为PriorityOrdered类型的后置处理器 、Ordered类型的后置处理器、普通类型的后置处理器被注册过一次了。重新注册的原因是:- 这是 SpringFramework 内置的既定策略,
MergedBeanDefinitionPostProcessor的实现类会收集Bean的初始化、销毁及自动注入相关的元数据信息 - 收集到的元数据信息,被用来在属性注入阶段给Bean进行依赖注入,在初始化阶段执行Bean的初始化方法(
@PostConstruct),在销毁阶段执行Bean的销毁方法(@PreDestroy)
- 这是 SpringFramework 内置的既定策略,
-
最后注册了一个
ApplicationListenerDetector,该后置处理器是用来注册监听器的:- 在Bean 的实例化和初始化之后,遍历所有的 Bean,检查其是否实现了
ApplicationListener接口,如果实现了接口并且作用域是单例,则将其注册到上下文的监听器集合中。
- 在Bean 的实例化和初始化之后,遍历所有的 Bean,检查其是否实现了
最后看下后置处理器的注册操作,它是如何存放到
AbstractBeanFactory中的
注册后置处理器方法,实际上是将后置处理器存入IOC容器的集合中,如下是注册方法源码:
private static void registerBeanPostProcessors(
ConfigurableListableBeanFactory beanFactory, List<BeanPostProcessor> postProcessors) {
if (beanFactory instanceof AbstractBeanFactory) {
// Bulk addition is more efficient against our CopyOnWriteArrayList there
((AbstractBeanFactory) beanFactory).addBeanPostProcessors(postProcessors);
}
else {
for (BeanPostProcessor postProcessor : postProcessors) {
beanFactory.addBeanPostProcessor(postProcessor);
}
}
}
进入beanFactory.addBeanPostProcessor中
public void addBeanPostProcessors(Collection<? extends BeanPostProcessor> beanPostProcessors) {
synchronized (this.beanPostProcessors) {
// Remove from old position, if any
this.beanPostProcessors.removeAll(beanPostProcessors);
// Add to end of list
this.beanPostProcessors.addAll(beanPostProcessors);
}
}
beanPostProcessors即为AbstractBeanFactory中的集合成员变量:
private final List<BeanPostProcessor> beanPostProcessors = new BeanPostProcessorCacheAwareList();
2.开始Bean的实例化
在上面源码位置的章节处,指出了
finishBeanFactoryInitialization方法会执行Bean的实例化、属性注入、初始化三个步骤
最关键的步骤就是该方法的最后一行preInstantiateSingletons:
protected void finishBeanFactoryInitialization(ConfigurableListableBeanFactory beanFactory) {
// ......
// Instantiate all remaining (non-lazy-init) singletons.
beanFactory.preInstantiateSingletons();
}
进入
preInstantiateSingletons,会来到DefaultListableBeanFactory类中,这里看其具体的方法逻辑。其中最关键的动作就是getBean方法,它会对非抽象的、非延迟加载、且是单实例作用域的Bean进行创建,而实例化就包含在创建过程中
preInstantiateSingletons 内主要的逻辑主要分为三步:
getMergedLocalBeanDefinition方法:获取合并Bean定义,根据合并Bean定义来判断此Bean是否为非抽象、非延迟加载的单例Bean,满足这三个条件才会进行创建getBean方法:满足上一步条件后,根据Bean名称进行Bean的创建,即执行Bean的实例化、属性注入、初始化afterSingletonsInstantiated方法:完成单实例Bean创建后通过此方法进行回调,执行一些创建完成后的自定义逻辑
public void preInstantiateSingletons() throws BeansException {
if (logger.isTraceEnabled()) {
logger.trace("Pre-instantiating singletons in " + this);
}
// 创建一个'bean定义名'副本集合
List<String> beanNames = new ArrayList<>(this.beanDefinitionNames);
// 触发所有非延迟单例Bean的创建
for (String beanName : beanNames) {
// 根据bean名称获取合并Bean定义,因为Bean定义也有子父类继承关系,需要合并后才能获得完整的配置信息
// 这里会获取解析配置类时得到的bean定义,主要用来进行下面的if判断
RootBeanDefinition bd = getMergedLocalBeanDefinition(beanName);
// 用合并后的bean定义进行判断,不是抽象的、不是延迟加载的单实例bean才会被处理
if (!bd.isAbstract() && bd.isSingleton() && !bd.isLazyInit()) {
// 这里是用来处理工厂Bean的
// FactoryBean默认懒加载,不会立即创建,除非指定 isEagerInit = true
if (isFactoryBean(beanName)) {
// 获取`工厂Bean`实例,
// ACTORY_BEAN_PREFIX是常量"&",这里是获取`FactoryBean`本身而不是它创建的Bean
Object bean = getBean(FACTORY_BEAN_PREFIX + beanName);
if (bean instanceof FactoryBean) {
FactoryBean<?> factory = (FactoryBean<?>) bean;
boolean isEagerInit;
// 当存在安全管理器`SecurityManager`时,使用特权操作进行检查
if (System.getSecurityManager() != null && factory instanceof SmartFactoryBean) {
// 如果isEagerInit为true,后面会对工厂Bean进行创建
isEagerInit = AccessController.doPrivileged(
(PrivilegedAction<Boolean>) ((SmartFactoryBean<?>) factory)::isEagerInit,
getAccessControlContext());
}
else {
// 没有安全管理时的isEagerInit检查
isEagerInit = (factory instanceof SmartFactoryBean &&
((SmartFactoryBean<?>) factory).isEagerInit());
}
// 如果isEagerInit = true,这里创建工厂Bean,进行其实例化、属性注入、初始化的过程
if (isEagerInit) {
getBean(beanName);
}
}
}
else {
// 这里是普通Bean的创建
getBean(beanName);
}
}
}
// 下面这段代码主要是执行`SmartInitializingSingleton`的`afterSingletonsInstantiated`方法
// 该方法的作用是:在所有的单例Bean已经被实例化、依赖注入、初始化后执行自定义逻辑。
// 因为此方法是创建单实例Bean的,所以`afterSingletonsInstantiated`方法是单实例bean的回调
for (String beanName : beanNames) {
// 从单例缓存中获取已初始化的Bean实例
Object singletonInstance = getSingleton(beanName);
// 判断该实例是否为`SmartInitializingSingleton`类型。如果是,则执行回调方法`afterSingletonsInstantiated`
if (singletonInstance instanceof SmartInitializingSingleton) {
// 使用`ApplicationStartup`对回调过程进行性能跟踪,记录回调的开始和结束
StartupStep smartInitialize = this.getApplicationStartup().start("spring.beans.smart-initialize")
.tag("beanName", beanName);
SmartInitializingSingleton smartSingleton = (SmartInitializingSingleton) singletonInstance;
// 如果启用了安全管理器,则通过AccessController以特权方式执行回调方法
if (System.getSecurityManager() != null) {
AccessController.doPrivileged((PrivilegedAction<Object>) () -> {
smartSingleton.afterSingletonsInstantiated();
return null;
}, getAccessControlContext());
}
// 否则,直接执行回调方法。
else {
smartSingleton.afterSingletonsInstantiated();
}
// ApplicationStartup结束记录
smartInitialize.end();
}
}
}
下面详细介绍三个步骤处理
第一步,合并Bean定义
进入上面的
getMergedLocalBeanDefinition方法,会来到AbstractBeanFactory容器类中
先从容器AbstractBeanFactory的缓存中获取BeanDefinition,获取不到再调用getMergedBeanDefinition方法获取:
protected RootBeanDefinition getMergedLocalBeanDefinition(String beanName) throws BeansException {
// Quick check on the concurrent map first, with minimal locking.
RootBeanDefinition mbd = this.mergedBeanDefinitions.get(beanName);
// bean定义不为空或未失效
if (mbd != null && !mbd.stale) {
return mbd;
}
// 1.先调用getBeanDefinition方法,去DefaultListableBeanFactory取出`BeanDefinition`
// 2.再调用getMergedBeanDefinition方法,获取合并后的bean定义
return getMergedBeanDefinition(beanName, getBeanDefinition(beanName));
}
着重看上面的
getMergedBeanDefinition方法,先看它的第二个参数getBeanDefinition,它是一个用来获取bean定义的方法
进入getBeanDefinition方法中,会来到容器类DefaultListableBeanFactory内。代码如下,这里获取的BeanDefinition就是通过解析配置类所得到的BeanDefinition(参考Bean定义阶段BeanDefinition的存储):
@Override
public BeanDefinition getBeanDefinition(String beanName) throws NoSuchBeanDefinitionException {
//在`DefaultListableBeanFactory`的bean定义集合中,根据bean名称取出bean定义
BeanDefinition bd = this.beanDefinitionMap.get(beanName);
if (bd == null) {
if (logger.isTraceEnabled()) {
logger.trace("No bean named '" + beanName + "' found in " + this);
}
throw new NoSuchBeanDefinitionException(beanName);
}
return bd;
}
然后回归
getMergedBeanDefinition方法本身,看bean定义是如何合并的:
先概括出总体合并逻辑:
- 尝试从缓存中获取已合并的Bean定义,获取到直接返回
- 没有获取到,则进行bean合并流程,但有两个分支:
- 当前bean没有父bean的情况,直接返回当前bean的bean定义(作为已合并的bean定义)
- 当前bean存在父bean,则进行当前bean与其父bean的
BeanDefinition合并,用子bean定义覆盖父bean定义,然后返回合并结果。注意,一般情况下子父bean的名称不同,如果出现相同的情况,代码会去父容器中获取父bean定义来与子bean定义进行合并
然后看源码:
protected RootBeanDefinition getMergedBeanDefinition(
String beanName, BeanDefinition bd, @Nullable BeanDefinition containingBd)
throws BeanDefinitionStoreException {
// 使用`mergedBeanDefinitions`缓存进行同步,确保并发安全
// `mergedBeanDefinitions`是一个ConcurrentHashMap,是一个用于存放`已合并的bean定义`的集合
synchronized (this.mergedBeanDefinitions) {
RootBeanDefinition mbd = null;
RootBeanDefinition previous = null;
// 如果`containingBd`为null,代表当前Bean不是内部Bean(即当前Bean没有被包含在另一个Bean中),
// 不是内部bean时,会尝试从缓存`mergedBeanDefinitions`中获取已合并的定义`mbd`,用以节约性能
if (containingBd == null) {
mbd = this.mergedBeanDefinitions.get(beanName);
}
// 如果缓存中没有已合并bean定义或者已过期,则进行合并操作
if (mbd == null || mbd.stale) {
// 保存旧的合并bean定义,用于后续的缓存信息复制
previous = mbd;
// 处理没有父bean的情况
if (bd.getParentName() == null) {
// 如果当前BeanDefinition已经是`RootBeanDefinition`,则克隆一份
if (bd instanceof RootBeanDefinition) {
mbd = ((RootBeanDefinition) bd).cloneBeanDefinition();
}
// 否则,创建一个新的`RootBeanDefinition`,复制`当前BeanDefinition`的属性到其中
else {
mbd = new RootBeanDefinition(bd);
}
}
// 处理有父bean的情况
else {
// 需要合并父子bean定义
BeanDefinition pbd;
try {
// 获取当前bean的父Bean的名字,并转换为规范名字(去除工厂前缀)
String parentBeanName = transformedBeanName(bd.getParentName());
// 如果父Bean的名字与当前Bean的名字不同,则递归调用`getMergedBeanDefinition`获取父Bean的合并定义
// 这里递归调用的原因是,父bean可能还有父bean,这里向上把当前bean及其所有父bean的bean定义全部合并处理
if (!beanName.equals(parentBeanName)) {
pbd = getMergedBeanDefinition(parentBeanName);
}
// 处理`父Bean名字`与当前`子Bean名字`相同的情况
// 在父子容器的场景下,子容器定义了与父容器同名的bean,就会在此处被处理
// 这里会尝试从父容器获取bean定义来进行合并,以防止子bean定义自己引用自己发生错误
else {
// 先获取父容器
BeanFactory parent = getParentBeanFactory();
// 如果父容器是可配置容器类型
if (parent instanceof ConfigurableBeanFactory) {
// 尝试从父容器中获取父bean定义
pbd = ((ConfigurableBeanFactory) parent).getMergedBeanDefinition(parentBeanName);
}else {
throw new NoSuchBeanDefinitionException(parentBeanName,
"Parent name '" + parentBeanName + "' is equal to bean name '" + beanName +"': cannot be resolved without a ConfigurableBeanFactory parent");
}
}
}
// 如果获取父定义失败,抛出异常
catch (NoSuchBeanDefinitionException ex) {
throw new BeanDefinitionStoreException(bd.getResourceDescription(), beanName,
"Could not resolve parent bean definition '" + bd.getParentName() + "'", ex);
}
// Deep copy with overridden values.
// 将父bean定义创建为一个新的`RootBeanDefinition`
mbd = new RootBeanDefinition(pbd);
// 然后使用子定义`bd`中的属性覆盖父定义中的属性,即合并
mbd.overrideFrom(bd);
}
// 如果合并后的定义没有设置作用域,则默认为单例
if (!StringUtils.hasLength(mbd.getScope())) {
mbd.setScope(SCOPE_SINGLETON);
}
// 如果当前Bean是包含在另一个非单例Bean中,那么即使当前Bean定义是单例,也要将其作用域设置为父Bean的作用域。
// 即:内部 Bean 必须与包含它的外部 Bean 作用域一致(如原型外部 Bean 的内部 Bean 不能是单例)。
if (containingBd != null && !containingBd.isSingleton() && mbd.isSingleton()) {
mbd.setScope(containingBd.getScope());
}
// 如果当前Bean不是内部Bean, `containingBd==null`
// 并且配置了允许缓存Bean元数据, `isCacheBeanMetadata()`
// 则将合并后的定义放入缓存`mergedBeanDefinitions`
if (containingBd == null && isCacheBeanMetadata()) {
// 存入缓存,这里关联了方法最开始的地方,二者是同一个集合。当再次获取相同bean时,就可以直接取了
this.mergedBeanDefinitions.put(beanName, mbd);
}
}
// 如果之前从缓存中获取的合并定义不为空,mbd.stale为true
// 则把旧合并定义中的`相关缓存信息`复制到新的合并定义中,复用相关属性以避免再次解析
if (previous != null) {
copyRelevantMergedBeanDefinitionCaches(previous, mbd);
}
// 返回合并后的Bean定义。如果当前bean没有父bean,这里返回的就是当前bean
return mbd;
}
}
注意点:
- 内部Bean(containingBd不为空)不会被缓存,因为它们是包含在外部Bean中的,每次都需要重新合并。
- 合并操作是一个深度复制的过程,确保不会修改原始的父定义和子定义。
- 递归获取父定义,因为父定义也可能有父定义,需要一直合并到根。
合并规则:
- 子定义中的属性会覆盖父定义中对应的属性。
- 对于某些属性(如
scope、lazyInit等),如果子定义没有设置,则使用父定义的值;如果子定义设置了,则覆盖父定义。
展示一个简单的合并示例:
假设有一个父Bean定义:
<bean id="parent" class="com.example.Parent" scope="prototype">
<property name="name" value="parent"/>
</bean>
子Bean定义:
<bean id="child" parent="parent">
<property name="age" value="10"/>
<scope>singleton</scope>
</bean>
合并后的子Bean定义:
class: com.example.Parent
scope: singleton (子定义覆盖了父定义的prototype)
properties: name=parent (继承自父), age=10 (子定义新增)
这个方法确保了在创建Bean实例之前,Bean定义已经是一个完整的、合并了所有父定义和子定义属性的RootBeanDefinition。
第二步,开始创建Bean
当获取的合并bean定义满足非抽象、非延迟加载、且为单例作用域的条件后,进入
getBean方法(在AbstractBeanFactory类中),该方法调用doGetBean方法来创建并实例化Bean
doGetBean 方法源码较长,先概括整体逻辑:
- 先尝试从缓存中取Bean,没有则创建
- 检查Bean是否已经正在创建中
- 获取父容器,如果当前容器不存在 创建bean所需 的定义信息,则尝试让父容器实例化这个bean
- 根据当前Bean名获取合并Bean定义(这里是第二次取,前面取了一次)
- 处理依赖关系,通过合并Bean定义把当前Bean所依赖的Bean先创建出来
- 最后,根据合并Bean定义获取当前Bean的作用域,不同作用域执行不同的创建流程,这里重点关注单实例bean的创建
protected <T> T doGetBean(
String name, @Nullable Class<T> requiredType, @Nullable Object[] args, boolean typeCheckOnly)
throws BeansException {
// 获取Bean的名称,主要是去除Bean名的工厂前缀'&',并根据别名获取正确Bean名
String beanName = transformedBeanName(name);
Object beanInstance;
// 尝试从缓存中获取Bean,如果获取到则直接返回,避免重复创建,节约性能。
// 此处尝试获取的是单实例的Bean。因为单实例bean只创建一次,所以需要缓存起来。如果当前Bean是第一次创建,这里不会获取到
Object sharedInstance = getSingleton(beanName);
if (sharedInstance != null && args == null) {
if (logger.isTraceEnabled()) {
if (isSingletonCurrentlyInCreation(beanName)) {
logger.trace("Returning eagerly cached instance of singleton bean '" + beanName +
"' that is not fully initialized yet - a consequence of a circular reference");
}
else {
logger.trace("Returning cached instance of singleton bean '" + beanName + "'");
}
}
// 处理从缓存中获取的bean实例,主要是判断该实例是普通的bean还是FactoryBean。
// 如果是FactoryBean,并且请求的bean名称没有`&`前缀,则返回FactoryBean创建的产品对象;否则,返回FactoryBean本身
// 如果只是普通bean,则直接返回
beanInstance = getObjectForBeanInstance(sharedInstance, name, beanName, null);
}
else {
// 检查当前bean是否存在于线程私有变量`prototypesCurrentlyInCreation`中,是则代表当前bean正在创建中,抛出异常
// `prototypesCurrentlyInCreation`是一个ThreadLocal,存放正在创建中的bean
// 即当前Bean已经正在创建中了,再创建可能发生了循环引用
if (isPrototypeCurrentlyInCreation(beanName)) {
throw new BeanCurrentlyInCreationException(beanName);
}
// 获取父容器
// 如果当前容器不存在需创建bean的定义信息,则尝试让父容器实例化当前bean
BeanFactory parentBeanFactory = getParentBeanFactory();
// 父容器不为空,且当前容器没有需创建bean的定义 ,使用父容器创建Bean
if (parentBeanFactory != null && !containsBeanDefinition(beanName)) {
// 获取原始bean名称
String nameToLookup = originalBeanName(name);
// 当父容器是`AbstractBeanFactory`类型时,去父容器中创建当前Bean
if (parentBeanFactory instanceof AbstractBeanFactory) {
return ((AbstractBeanFactory) parentBeanFactory).doGetBean(
nameToLookup, requiredType, args, typeCheckOnly);
}
// 父容器不是`AbstractBeanFactory`类型,且方法参数不为空
else if (args != null) {
// 使用方法参数委托父容器创建bean
return (T) parentBeanFactory.getBean(nameToLookup, args);
}
else if (requiredType != null) {
// 没有参数时,通过bean的请求类型委托给父容器的标准getBean方法进行创建
return parentBeanFactory.getBean(nameToLookup, requiredType);
}
else {
// 在父容器中使用原始bean名称进行创建
return (T) parentBeanFactory.getBean(nameToLookup);
}
}
// 标记当前bean已经开始被创建了
if (!typeCheckOnly) {
markBeanAsCreated(beanName);
}
// 使用 ApplicationStartup 监控 Bean 创建过程
StartupStep beanCreation = this.applicationStartup.start("spring.beans.instantiate")
.tag("beanName", name);
try {
// 请求的Bean类型不为空,进行记录
if (requiredType != null) {
beanCreation.tag("beanType", requiredType::toString);
}
// 此处会合并BeanDefinition,因为之前调用过一次,所以这里会直接取缓存:
// 会去`DefaultListableBeanFactory`的`bean定义集合`中取出`BeanDefinition`
RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName);
// 检查Bean是否为抽象的(如果是则会抛出无法实例化的异常)
checkMergedBeanDefinition(mbd, beanName, args);
// 接下来是处理依赖关系,把当前bean所依赖的bean创建出来
// 获取当前Bean定义中需依赖Bean的bean名
String[] dependsOn = mbd.getDependsOn();
// 如果依赖的bean不为空,则遍历进行循环依赖检测
if (dependsOn != null) {
for (String dep : dependsOn) {
// 发生循环依赖则抛出异常
if (isDependent(beanName, dep)) {
throw new BeanCreationException(mbd.getResourceDescription(), beanName,
"Circular depends-on relationship between '" + beanName + "' and '" + dep + "'");
}
// 对依赖关系进行记录
registerDependentBean(dep, beanName);
try {
// 创建需依赖的bean
getBean(dep);
}
catch (NoSuchBeanDefinitionException ex) {
throw new BeanCreationException(mbd.getResourceDescription(), beanName,
"'" + beanName + "' depends on missing bean '" + dep + "'", ex);
}
}
}
/************************************* 这里是创建单实例的Bean ************************************/
if (mbd.isSingleton()) {
// `getSingleton`方法会再次尝试从一级缓存获取Bean,如果没有取到,会把当前Bean标记为正在创建中的Bean
// 然后调用`createBean`方法创建Bean
sharedInstance = getSingleton(beanName, () -> {
try {
return createBean(beanName, mbd, args);
}
catch (BeansException ex) {
// 如果创建过程中出现异常
// 从`一二三级缓存`和`保存已注册bean名的集合`中移除当前单实例Bean,然后执行当前Bean的销毁操作
destroySingleton(beanName);
throw ex;
}
});
// 获取bean实例,如果是工厂bean返回其创建的bean;普通bean则返回其本身
beanInstance = getObjectForBeanInstance(sharedInstance, name, beanName, mbd);
}
/************************************* 这里是创建原型Bean ************************************/
else if (mbd.isPrototype()) {
// It's a prototype -> create a new instance.
Object prototypeInstance = null;
try {
// 创建前的处理方法,把当前需创建的原型Bean存到`ThreadLocal`(当前线程的私有变量)中
// 如果当前线程中有多个正在创建的原型Bean,则把这些bean存入Set集合,再把Set集合存入`ThreadLocal`
beforePrototypeCreation(beanName);
// 进行原型Bean的创建
prototypeInstance = createBean(beanName, mbd, args);
}
finally {
// 对应上面的`beforePrototypeCreation`方法,这里是从`ThreadLocal`中移除
afterPrototypeCreation(beanName);
}
// 获取bean实例,如果是工厂bean返回其创建的bean;普通bean则返回其本身
beanInstance = getObjectForBeanInstance(prototypeInstance, name, beanName, mbd);
}
/*********************** 这里是非单例非原型的其他作用域Bean的创建,包括自定义作用域 *********************/
else {
// 获取作用域名称并校验
String scopeName = mbd.getScope();
if (!StringUtils.hasLength(scopeName)) {
throw new IllegalStateException("No scope name defined for bean '" + beanName + "'");
}
// 获取作用域实现
Scope scope = this.scopes.get(scopeName);
if (scope == null) {
throw new IllegalStateException("No Scope registered for scope name '" + scopeName + "'");
}
try {
// 执行Bean创建,先去对应作用域实现缓存中去取,取不到就通过lamdba中的`createBean`创建
Object scopedInstance = scope.get(beanName, () -> {
// 创建前的处理方法,把当前需创建的Bean存到`ThreadLocal`(当前线程的私有变量)中
// 如果当前线程中有多个正在创建的Bean,则把这些bean存入Set集合,再把Set集合存入`ThreadLocal`
beforePrototypeCreation(beanName);
try {
// 创建
return createBean(beanName, mbd, args);
}
finally {
// 对应上面的`beforePrototypeCreation`方法,这里是从`ThreadLocal`中移除
afterPrototypeCreation(beanName);
}
});
// 获取bean实例,如果是工厂bean返回其创建的bean;普通bean则返回其本身
beanInstance = getObjectForBeanInstance(scopedInstance, name, beanName, mbd);
}
catch (IllegalStateException ex) {
throw new ScopeNotActiveException(beanName, scopeName, ex);
}
}
}
catch (BeansException ex) {
// 在监控中记录异常信息
beanCreation.tag("exception", ex.getClass().toString());
beanCreation.tag("message", String.valueOf(ex.getMessage()));
cleanupAfterBeanCreationFailure(beanName);
throw ex;
}
finally {
// 结束`ApplicationStartup`监控
beanCreation.end();
}
}
// 返回bean实例。如果`requiredType`不为空,将Bean实例的类型转换`requiredType`的类型
return adaptBeanInstance(name, beanInstance, requiredType);
}
doGetBean方法中重要的有两处:中间的getMergedLocalBeanDefinition方法合并BeanDefinition,以及下面的createBean方法:
注意: 这里的获取合并bean定义的方法 getMergedLocalBeanDefinition 是第二次调用,之前的preInstantiateSingletons方法已经使用了一次。
-
第一次调用获取
BeanDefinition,作用是判断要初始化的bean是否为非抽象的、非延迟加载的单实例bean -
第二次调用获取
BeanDefinition,作用是拿BeanDefinition去实例化bean。而且经过前一次调用后这里可以直接取缓存。
核心逻辑:
- 合并
BeanDefinition,合并的逻辑是自下而上递归寻找父BeanDefinition,再从上到下合并获得最终的BeanDefinition - 通过合并后的
BeanDefinition对不同作用域的bean进行不同的创建处理
去除繁杂的源码,最核心的部分如下:
protected <T> T doGetBean(String name, @Nullable Class<T> requiredType, @Nullable Object[] args, boolean typeCheckOnly)
throws BeansException {
// 获取Bean的名称
String beanName = transformedBeanName(name);
Object bean;
// 尝试从一级缓存中获取Bean,如果获取到则直接返回,避免重复创建,节约性能。
// 因为单实例bean只创建一次,所以需要缓存起来。如果当前Bean是第一次创建,这里不会获取到
Object sharedInstance = getSingleton(beanName);
if (sharedInstance != null && args == null) {
// logger ......
bean = getObjectForBeanInstance(sharedInstance, name, beanName, null);
}
else {
// ..............
try {
// 此处会合并BeanDefinition,并检查是否为抽象类(abstract则会抛出无法实例化的异常)
// 会去DefaultListableBeanFactory的 bean定义集合 中取出`BeanDefinition`
RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName);
// ............
// 单实例bean的创建,最终调用createBean
if (mbd.isSingleton()) {
sharedInstance = getSingleton(beanName, () -> {
try {
return createBean(beanName, mbd, args);
} // catch ......
});
bean = getObjectForBeanInstance(sharedInstance, name, beanName, mbd);
}
// 其他作用域Bean的创建........
}
// ......
}
下面深入单实例Bean的创建过程
单实例 bean 的创建,是在 getSingleton 方法的 lambda 参数中调用的:
- 这个 lambda表达式返回的是一个
ObjectFactory,因为单实例 bean 只能创建一次,第二次再获取就需要从缓存(一级缓存singletonObjects)中获取了 - 如果创建bean时在
getSingleton方法没有单实例bean的缓存,该lambda表达式就会使用createBean方法创建一个单实例bean,并存入单实例bean的缓存中
原型 bean 没有缓存的必要,每次获取都会创建新的 bean 对象出来
注意:前面限制了要初始化的bean为非抽象的、非延迟加载的单实例bean,此处还有原型bean处理的原因是因为doGetBean方法是通用设计的,会有其他的场景来调用它,所以没有去掉原型bean的处理
// 创建单实例bean
if (mbd.isSingleton()) {
sharedInstance = getSingleton(beanName, () -> {
try {
return createBean(beanName, mbd, args);
} // catch ......
});
bean = getObjectForBeanInstance(sharedInstance, name, beanName, mbd);
}
// 创建原型bean
else if (mbd.isPrototype()) {
Object prototypeInstance = null;
try {
beforePrototypeCreation(beanName);
prototypeInstance = createBean(beanName, mbd, args);
}
finally {
afterPrototypeCreation(beanName);
}
bean = getObjectForBeanInstance(prototypeInstance, name, beanName, mbd);
}
进入getSingleton,此方法会先尝试从一级缓存singletonObjects中获取bean,如果取不到再执行createBean方法进行创建:
public Object getSingleton(String beanName, ObjectFactory<?> singletonFactory) {
// 检查beanName非空
Assert.notNull(beanName, "Bean name must not be null");
// 加锁确保线程安全(单实例bean的创建线程)
// singletonObjects是一级缓存,用于存放已经创建好的bean(已经完成实例化、属性注入、初始化的完整bean)
synchronized (this.singletonObjects) {
// 从一级缓存中获取bean,如果存在则直接返回
Object singletonObject = this.singletonObjects.get(beanName);
// 当一级缓存获取不到bean时
if (singletonObject == null) {
// 如果一级缓存不存在bean,检查当前bean是否处于销毁状态,如果是则抛出异常。因为不允许在销毁过程中创建bean
if (this.singletonsCurrentlyInDestruction) {
throw new BeanCreationNotAllowedException(beanName,
"Singleton bean creation not allowed while singletons of this factory are in destruction " +
"(Do not request a bean from a BeanFactory in a destroy method implementation!)");
}
if (logger.isDebugEnabled()) {
logger.debug("Creating shared instance of singleton bean '" + beanName + "'");
}
// 将bean名称添加到`正在创建的单例bean集合`中,该集合名为singletonsCurrentlyInCreation
beforeSingletonCreation(beanName);
boolean newSingleton = false;
boolean recordSuppressedExceptions = (this.suppressedExceptions == null);
if (recordSuppressedExceptions) {
this.suppressedExceptions = new LinkedHashSet<>();
}
try {
// 进行bean的创建,这里的singletonFactory是传入的lamdba表达式,使用createBean方法创建bean
// 所以此处就是执行外面那个createBean方法来创建bean
singletonObject = singletonFactory.getObject();
// 如果创建成功,设置newSingleton标志为true,表示创建了新单实例bean
newSingleton = true;
}
catch (IllegalStateException ex) {
// Has the singleton object implicitly appeared in the meantime ->
// if yes, proceed with it since the exception indicates that state.
singletonObject = this.singletonObjects.get(beanName);
if (singletonObject == null) {
throw ex;
}
}
catch (BeanCreationException ex) {
if (recordSuppressedExceptions) {
for (Exception suppressedException : this.suppressedExceptions) {
ex.addRelatedCause(suppressedException);
}
}
throw ex;
}
// 最后一定调用的
finally {
if (recordSuppressedExceptions) {
this.suppressedExceptions = null;
}
// 将当前bean的名称从`正在创建的单例bean集合`中移除
afterSingletonCreation(beanName);
}
// 如果成功创建了新的单实例bean,则将单例bean对象添加到一级缓存,并清除二、三级缓存。
if (newSingleton) {
addSingleton(beanName, singletonObject);
}
}
// 最后返回bean
return singletonObject;
}
}
下面进入
getSingleton的createBean方法,它实际执行了Bean的创建。该方法进一步调用了AbstractAutowireCapableBeanFactory的createBean方法:
protected Object createBean(String beanName, RootBeanDefinition mbd, @Nullable Object[] args)
throws BeanCreationException {
// 日志记录
if (logger.isTraceEnabled()) {
logger.trace("Creating instance of bean '" + beanName + "'");
}
// 创建Bean定义副本
RootBeanDefinition mbdToUse = mbd;
// 根据Bean定义及名称,解析出此Bean的实际类
Class<?> resolvedClass = resolveBeanClass(mbd, beanName);
// 如果解析出的类不为空,且类未被设置到bean定义中
if (resolvedClass != null && !mbd.hasBeanClass() && mbd.getBeanClassName() != null) {
// 创建出一个新的Bean定义,并将解析出的实际类设置到其中
mbdToUse = new RootBeanDefinition(mbd);
mbdToUse.setBeanClass(resolvedClass);
}
try {
// 处理方法重写, 即 lookup-method 和 replaced-method 的配置处理
mbdToUse.prepareMethodOverrides();
}
catch (BeanDefinitionValidationException ex) {
throw new BeanDefinitionStoreException(mbdToUse.getResourceDescription(),
beanName, "Validation of method overrides failed", ex);
}
try {
// 执行后置处理器`InstantiationAwareBeanPostProcessor`,用来返回代理对象(如果有的话)
// 该处理器的'postProcessBeforeInstantiation'方法如果有值,则'postProcessAfterInstantiation'方法也会执行
Object bean = resolveBeforeInstantiation(beanName, mbdToUse);
// 执行后置处理器有结果,则返回结果并结束方法
if (bean != null) {
return bean;
}
}
catch (Throwable ex) {
throw new BeanCreationException(mbdToUse.getResourceDescription(), beanName,
"BeanPostProcessor before instantiation of bean failed", ex);
}
try {
// 实际执行Bean的创建流程
Object beanInstance = doCreateBean(beanName, mbdToUse, args);
if (logger.isTraceEnabled()) {
logger.trace("Finished creating instance of bean '" + beanName + "'");
}
return beanInstance;
}
catch (BeanCreationException | ImplicitlyAppearedSingletonException ex) {
// A previously detected exception with proper bean creation context already,
// or illegal singleton state to be communicated up to DefaultSingletonBeanRegistry.
throw ex;
}
catch (Throwable ex) {
throw new BeanCreationException(
mbdToUse.getResourceDescription(), beanName, "Unexpected exception during bean creation", ex);
}
}
分为两步:
-
resolveBeforeInstantiation:会调用InstantiationAwareBeanPostProcessor的postProcessBeforeInstantiation方法,作用是创建代理 bean 而不是目标 bean 实例,但只有在该方法有非null返回值时才会创建:protected Object resolveBeforeInstantiation(String beanName, RootBeanDefinition mbd) { Object bean = null; if (!Boolean.FALSE.equals(mbd.beforeInstantiationResolved)) { // Make sure bean class is actually resolved at this point. if (!mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) { Class<?> targetType = determineTargetType(beanName, mbd); if (targetType != null) { // 执行所有InstantiationAwareBeanPostProcessor bean = applyBeanPostProcessorsBeforeInstantiation(targetType, beanName); if (bean != null) { // 如果成功创建出了bean,则执行BeanPostProcessor的后置初始化 bean = applyBeanPostProcessorsAfterInitialization(bean, beanName); } } } mbd.beforeInstantiationResolved = (bean != null); } return bean; }postProcessBeforeInstantiation方法什么情况下会返回非null对象:- 通常由特定的
InstantiationAwareBeanPostProcessor实现来决定,比如需要提前暴露代理(例如处理循环依赖)或者有特殊的代理需求(例如使用Objenesis来创建实例)时,可能会返回代理对象。 - 另外,需要注意的是,如果我们自定义了
InstantiationAwareBeanPostProcessor,在其postProcessBeforeInstantiation方法中返回了一个对象,那么Spring就会使用这个对象作为Bean,并且不会执行默认的实例化过程。
- 通常由特定的
-
doCreateBean:真正创建 bean,这个方法中共有三个大步骤:- 实例化 bean 对象
- 属性赋值 & 依赖注入
- bean 对象的初始化
第三步,实例化Bean
这里重点介绍实例化 bean 对象,进入
doCreateBean方法中:
在此方法中,bean实例化的触发点是createBeanInstance,翻译过来就是创建bean实例:
protected Object doCreateBean(String beanName, RootBeanDefinition mbd, @Nullable Object[] args)
throws BeanCreationException {
BeanWrapper instanceWrapper = null;
// 如果是单例bean,先尝试从FactoryBean缓存中进行获取,取到则将其从缓存中删除
if (mbd.isSingleton()) {
instanceWrapper = this.factoryBeanInstanceCache.remove(beanName);
}
// 如果缓存中没有,则创建此Bean的实例
if (instanceWrapper == null) {
// 进行Bean的实例化
instanceWrapper = createBeanInstance(beanName, mbd, args);
}
/******************************* 这里向下是属性注入与初始化了,可以先不看 *************************************/
Object bean = instanceWrapper.getWrappedInstance();
// 获取此Bean的实际类型
Class<?> beanType = instanceWrapper.getWrappedClass();
// Bean类型不是null则设置到Bean定义中
if (beanType != NullBean.class) {
mbd.resolvedTargetType = beanType;
}
// 这里开始是初始化
// 收集Bean的 初始化、销毁及自动注入 相关的元数据信息
synchronized (mbd.postProcessingLock) {
if (!mbd.postProcessed) {
try {
// 执行MergedBeanDefinitionPostProcessor处理器
applyMergedBeanDefinitionPostProcessors(mbd, beanType, beanName);
}
catch (Throwable ex) {
throw new BeanCreationException(mbd.getResourceDescription(), beanName,
"Post-processing of merged bean definition failed", ex);
}
mbd.postProcessed = true;
}
}
// 处理循环依赖
boolean earlySingletonExposure = (mbd.isSingleton() && this.allowCircularReferences &&
isSingletonCurrentlyInCreation(beanName));
if (earlySingletonExposure) {
if (logger.isTraceEnabled()) {
logger.trace("Eagerly caching bean '" + beanName +
"' to allow for resolving potential circular references");
}
// 获取一个早期Bean引用,并将其放入三级缓存
addSingletonFactory(beanName, () -> getEarlyBeanReference(beanName, mbd, bean));
}
Object exposedObject = bean;
try {
// 属性注入
populateBean(beanName, mbd, instanceWrapper);
// 初始化处理,包括执行初始化方法、执行Aware回调等
exposedObject = initializeBean(beanName, exposedObject, mbd);
}
catch (Throwable ex) {
if (ex instanceof BeanCreationException && beanName.equals(((BeanCreationException) ex).getBeanName())) {
throw (BeanCreationException) ex;
}
else {
throw new BeanCreationException(
mbd.getResourceDescription(), beanName, "Initialization of bean failed", ex);
}
}
if (earlySingletonExposure) {
// 获取单实例Bean的早期引用
Object earlySingletonReference = getSingleton(beanName, false);
if (earlySingletonReference != null) {
if (exposedObject == bean) {
exposedObject = earlySingletonReference;
}
// 检查提前暴露的引用和最终 Bean 是否一致
else if (!this.allowRawInjectionDespiteWrapping && hasDependentBean(beanName)) {
String[] dependentBeans = getDependentBeans(beanName);
Set<String> actualDependentBeans = new LinkedHashSet<>(dependentBeans.length);
for (String dependentBean : dependentBeans) {
if (!removeSingletonIfCreatedForTypeCheckOnly(dependentBean)) {
actualDependentBeans.add(dependentBean);
}
}
if (!actualDependentBeans.isEmpty()) {
throw new BeanCurrentlyInCreationException(beanName,
"Bean with name '" + beanName + "' has been injected into other beans [" +
StringUtils.collectionToCommaDelimitedString(actualDependentBeans) +
"] in its raw version as part of a circular reference, but has eventually been " +
"wrapped. This means that said other beans do not use the final version of the " +
"bean. This is often the result of over-eager type matching - consider using " +
"'getBeanNamesForType' with the 'allowEagerInit' flag turned off, for example.");
}
}
}
}
try {
// 注册销毁处理
registerDisposableBeanIfNecessary(beanName, bean, mbd);
}
catch (BeanDefinitionValidationException ex) {
throw new BeanCreationException(
mbd.getResourceDescription(), beanName, "Invalid destruction signature", ex);
}
return exposedObject;
}
进入
createBeanInstance方法中,查看实例化bean对象过程:
此方法支持多种实例化Bean的策略,按优先级依次为:
- Supplier 实例化:用于执行自定义的bean实例化,有最高优先级,当存在函数式接口Supplier的自定义实例化方法时执行
- 工厂方法实例化:当存在工厂方法时,使用工厂方法进行实例化。支持静态和实例工厂方法
- 构造函数自动装配:通过后置处理器选择一个构造方法进行bean的实例化,如果bean中使用了构造方法进行依赖注入,这里还会执行相关的注入
- 默认构造函数:如果上述三个条件都不满足,即不存在函数式接口Supplier的自定义实例化方法、不存在工厂实例化方法、无法通过后置处理器获取构造方法且没有进行构造器依赖注入时,则使用默认无参构造方法进行最简单的实例化
protected BeanWrapper createBeanInstance(String beanName, RootBeanDefinition mbd, @Nullable Object[] args) {
// 解析出bean的类型
Class<?> beanClass = resolveBeanClass(mbd, beanName);
// 如果bean类不是public的,且该类不允许非public访问(默认是允许的),则抛出异常
if (beanClass != null && !Modifier.isPublic(beanClass.getModifiers()) && !mbd.isNonPublicAccessAllowed()) {
throw new BeanCreationException(mbd.getResourceDescription(), beanName,
"Bean class isn't public, and non-public access not allowed: " + beanClass.getName());
}
// 通过函数式接口Supplier来执行bean的创建
// 此Supplier为完全自定义的实例创建过程,会跳过 Spring 标准逻辑
// Supplier是在bean定义中设置的,其使用场景:编程式Bean定义注册时,可以使用Supplier提供实例创建逻辑
Supplier<?> instanceSupplier = mbd.getInstanceSupplier();
if (instanceSupplier != null) {
return obtainFromSupplier(instanceSupplier, beanName);
}
// 如果Bean定义中指定了工厂方法,则使用工厂方法实例化。会反射调用工厂方法来进行bean的实例化,有两种工厂方法
// 静态工厂:factory-method 指定静态方法。
// 实例工厂:factory-bean + factory-method 组合。
if (mbd.getFactoryMethodName() != null) {
return instantiateUsingFactoryMethod(beanName, mbd, args);
}
// 性能优化处理,如果之前解析过,则使用之前的解析结果
boolean resolved = false;
boolean autowireNecessary = false;
if (args == null) {
synchronized (mbd.constructorArgumentLock) {
// 检查是否已经解析过构造函数或工厂方法
if (mbd.resolvedConstructorOrFactoryMethod != null) {
resolved = true;
autowireNecessary = mbd.constructorArgumentsResolved;
}
}
}
// 如果已经解析过,直接使用之前解析的结果,避免重复解析
if (resolved) {
if (autowireNecessary) {
// 需要自动装配构造函数时调用此方法
return autowireConstructor(beanName, mbd, null, null);
}
else {
// 不需要自动装配,使用默认构造函数
return instantiateBean(beanName, mbd);
}
}
// 当满足如下任一条件时,通过构造方法进行Bean的实例化
// 1. 通过SmartInstantiationAwareBeanPostProcessor后置处理器找到了构造器
// 2. 配置了注入方式是AUTOWIRE_CONSTRUCTOR,即构造器注入
// 3. 定义bean的时候指定了constructor-arg,它是用于注入构造函数参数的标签,在xml的<bean>标签中指定
// 4. 构造bean时传入了args参数
Constructor<?>[] ctors = determineConstructorsFromBeanPostProcessors(beanClass, beanName);
if (ctors != null || mbd.getResolvedAutowireMode() == AUTOWIRE_CONSTRUCTOR ||
mbd.hasConstructorArgumentValues() || !ObjectUtils.isEmpty(args)) {
//使用构造方法实例化bean
return autowireConstructor(beanName, mbd, ctors, args);
}
// 从bean定义中获取首选构造函数来对bean进行创建,这里的首选构造函数获取方式有两个
// 1.检测 Kotlin 类的主构造函数来获取
// 2.上面的获取不到,就获取所有public修饰的构造方法
ctors = mbd.getPreferredConstructors();
if (ctors != null) {
return autowireConstructor(beanName, mbd, ctors, null);
}
// 这里用于兜底,如果上面都没能创建bean,这里会通过反射调用无参构造函数创建
return instantiateBean(beanName, mbd);
}
obtainFromSupplier与instantiateUsingFactoryMethod这两段源码,提供了自定义与工厂方法的Bean实例化策略:
-
如果在编程式注册
BeanDefinition时使用Supplier,则走obtainFromSupplier进行自定义创建// 编程式注册Bean定义时使用Supplier GenericBeanDefinition beanDefinition = new GenericBeanDefinition(); beanDefinition.setBeanClass(MyBean.class); beanDefinition.setInstanceSupplier(() -> { MyBean bean = new MyBean(); bean.setCustomProperty("customValue"); return bean; }); registry.registerBeanDefinition("myBean", beanDefinition); -
如果在
BeanDefinition中指定了工厂类型的创建逻辑,则直接走工厂创建<!-- 静态工厂方法 --> <bean id="myBean" class="com.example.MyFactory" factory-method="createInstance"/> <!-- 实例工厂方法 --> <bean id="factory" class="com.example.MyFactory"/> <bean id="myBean" factory-bean="factory" factory-method="createInstance"/> -
除此之外,最重要的是
determineConstructorsFromBeanPostProcessors方法,它调用了后置处理器SmartInstantiationAwareBeanPostProcessor,该处理器会获取并解析实例化 bean 需要的构造器。如果bean中使用了构造方法进行依赖注入,Spring会调用AutowiredAnnotationBeanPostProcessor(SmartInstantiationAwareBeanPostProcessor的实现类) 的determineCandidateConstructors方法,它会返回一个构造器数组,然后在autowireConstructor方法中,选择一个标注了@Autowired的构造器实例化bean并执行注入。 -
而最后一行的
instantiateBean方法,会在上述场景都没有的情况下执行,它会通过反射机制,调用默认的无参构造器实例化 bean 对象。
最后createBeanInstance会返回bean实例,完成实例化阶段,将bean实例返回到doCreateBean方法中,继续向下进行属性注入与初始化。
1037

被折叠的 条评论
为什么被折叠?



