博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Spring Bean实例化过程
阅读量:6903 次
发布时间:2019-06-27

本文共 2272 字,大约阅读时间需要 7 分钟。

上篇中, 记录了Spring扫描Class, 封装成一个个BeanDefinition的过程, ApplicationContext后续将根据这些Bean定义来创建Bean实例, BeanDefinition和Bean实例保存在的位置如下:

BeanDefinition保存到的实例变量(DefaultListableBeanFactory):

/** List of bean definition names, in registration order */List
beanDefinitionNames/** Map from bean name to merged RootBeanDefinition */Map
mergedBeanDefinitions

Bean实例保存到的成员变量(DefaultListableBeanFactory):

/** 保存单例对象: bean名 --> bean实例 */private final Map
singletonObjects = new ConcurrentHashMap
(256);

一个[BeanDefinition]到一个[Bean实例]是通过BeanFactory#getBean方法完成的:

BeanFactory#getBean方法执行过程:

Tags:(BeanFactory具体对应的子类是DefaultListableBeanFactory)

  1. 从单例缓存singletonObjects查找, 有则直接返回

没有则

  1. 创建实例
  2. 执行bean后置处理器,调用Bean初始化方法
    依赖注入是后置处理完成的,也是调用BeanFactory#getBean获取依赖对象
  3. 保存实例到singletonObjects中

参考: [调用beanFactory.getBean获取/创建实例]节点

问题记录

1. 实例化Bean的位置

在上下文刷新时AbstractApplicationContext#refresh

// 执行完全部的BeanFactory后置处理// ConfigurationClassPostProcessor会加载工程下的class到BeanDefinition// 注册Bean后置处理器// 根据BeanDefinition实例化所有单例Bean.finishBeanFactoryInitialization(beanFactory);

2. 对象循环引用问题

getBean方法通过Bean后置处理器AutowiredAnnotationBeanPostProcessor注入依赖, 该后置处理器又将调用getBean获取依赖Bean, 例如有如下代码:

@Servicepublic class ServiceA {    @Autowired    ServiceB serviceB;}@Servicepublic class ServiceB {    @Autowired    ServiceA serviceA;}

BeanFactory会将创建中的bean名保存到singletonsCurrentlyInCreation, 创建中的bean实例保存到singletonFactories。

getBean("serviceA")的过程:

  1. 创建ServiceA实例
  2. 创建ServiceB实例
  3. 实例ServiceA注入到ServiceB (实例ServiceA仍在初始化中)
  4. ServiceB完成创建
  5. 实例ServiceB注入到ServiceA
  6. ServiceA完成创建

被依赖的Bean会先完成初始化

参考图片链接:

3. 单例Bean创建后注册到哪了?

DefaultSingletonBeanRegistry对象的singletonObjects字段, 这里注册的都是依赖已经注入, 且执行完Bean后置处理器的实例

/** Cache of singleton objects: bean name --> bean instance */private final Map
singletonObjects = new ConcurrentHashMap
(256);

4. 对象循环依赖异常

BeanCreationException: Circular depends-on relationship between

循环依赖会导致该异常, 如使用@DependsOn注解配置了依赖:

@Service@DependsOn("permission")public class Role {    @Autowired    private Permission permission;}@Service@DependsOn("role")public class Permission {    @Autowired    private Role role;}

Permission,Role互相依赖, 谁无法被创建, BeanFactory将抛出异常

BeanCreationException:
Circular depends-on relationship between 'role' and 'permission'

转载地址:http://yrpdl.baihongyu.com/

你可能感兴趣的文章
SCCM OSD部署排错
查看>>
十道非常好的shell脚本试题
查看>>
app项目案例一手机浏览器
查看>>
java 中 isEmpty和isBlank区别
查看>>
申请SSL证书怎样验证域名所有权
查看>>
麒麟开源堡垒机集中管控平台软件简介
查看>>
第十一单元练习
查看>>
从零开始的linux 第十六章
查看>>
EOS内存RAM是如何买卖的
查看>>
微服务架构中zuul的两种隔离机制实验
查看>>
电子合同将取代纸质合同吗?
查看>>
官宣丨“创客集结号”成功接入“广东省教育资源公共服务平台”!
查看>>
mock.js与json schema
查看>>
转:Java properties | FileNotFoundException: properties (系统找不到指定的文件。)
查看>>
Cpp中流继承关系
查看>>
Angular CLI 使用教程指南参考
查看>>
[设计模式之禅读书笔记]001_设计模式六大原则(一):单一职责原则(Single Responsibility Principle)...
查看>>
CSAPP:cachelab(1)
查看>>
时间序列识别代码调试版本1
查看>>
Tomcat内存溢出解决办法
查看>>