0
点赞
收藏
分享

微信扫一扫

Spring IOC源码解析:Spring Bean生命周期详解(一)


Spring IOC源码解析:Spring Bean生命周期详解(一)_初始化

DefaultListableBeanFactory继承体系

Spring IOC源码解析:Spring Bean生命周期详解(一)_spring_02

BeanFactory:Bean工厂,用来生产Bean
ConfigurableBeanFactory:提供配置工厂的方法
AutowireCapableBeanFactory:创建Bean,自动注入,初始化以及应用BeanPostProcessor
HierarchicalBeanFactory:获取父工厂
ListableBeanFactory:迭代的方式获取Bean
ConfigurableListableBeanFactory:指定忽略类型及清单
FactoryBeanRegistrySupport:增加对FactoryBean的支持
DefaultListableBeanFactory:最常用的BeanFactory实现类

AliasRegistry:定义对别名的增删查操作
SimpleAliasRegistry:对AliasRegistry进行实现。使用map保存 bean的别名->bean的名字 的映射关系
BeanDefinitionRegistry:定义对BeanDefinition的增删查操作
SingletonBeanRegistry:实现对单例Bean的注册和互殴去
DefaultSingletonBeanRegistry:对SingletonBeanRegistry进行实现。用map保存生成的单例Bean

因为初始化非延迟单例Bean的调用链路比较深,我先画一个简图,后续源码解析都围绕这个简图来展开。你可以先看一下这个简图,后续看源码就非常容易理解了!

Spring IOC源码解析:Spring Bean生命周期详解(一)_spring_03


Spring Bean生命周期的过程比较复杂,因此我用两节来分享。第一节了解Bean生命周期的主要执行链路,涉及到BeanPostProcessor执行的部分全部跳过。第二季主要分析BeanPostProcessor的执行部分。

这样先了解执行链路,再了解执行细节的方式,大家更容易接受,也不会晕车。毫不夸张的说,搞懂了Spring生命周期,就把Spring搞懂了一半

实例化Bean的几种方式

我们常用的实例化Bean的方式有如下几种

  1. 构造方法实例化 Bean
  2. 静态方法实例化 Bean
  3. Bean工厂方法实例化 Bean
  4. FactoryBean实例化 Bean

写个demo演示一下这几种方式

Spring IOC源码解析:Spring Bean生命周期详解(一)_初始化_04


Spring IOC源码解析:Spring Bean生命周期详解(一)_单例模式_05


Spring IOC源码解析:Spring Bean生命周期详解(一)_spring_06

Spring IOC源码解析:Spring Bean生命周期详解(一)_初始化_07


Spring IOC源码解析:Spring Bean生命周期详解(一)_单例模式_08


可以看到当我们用FactoryBean实现类的名字来获取Bean时,获取到的并不是FactoryBean,而是调用FactoryBean#getObject方法创建出来的对象。

我们我们如何获取FactoryBean对象呢?只需要在名字前面加一个&即可

初始化非延迟单例Bean

DefaultListableBeanFactory#preInstantiateSingletons

Spring IOC源码解析:Spring Bean生命周期详解(一)_java_09


这个方法后面还有回调SmartInitializingSingleton#afterSingletonsInstantiated方法,这其实是Bean生命周期中的初始化完成阶段,我们下节详细分析AbstractBeanFactory#doGetBean

Spring IOC源码解析:Spring Bean生命周期详解(一)_单例模式_10


首先先从1,2,3级缓存中取,取不到再进行下面的创建过程

Spring IOC源码解析:Spring Bean生命周期详解(一)_spring_11


AbstractAutowireCapableBeanFactory#createBean(删除部分代码)

Spring IOC源码解析:Spring Bean生命周期详解(一)_java_12


先执行实例化前阶段的逻辑,然后再调用doCreateBean进行创建AbstractAutowireCapableBeanFactory#doCreateBean

Spring IOC源码解析:Spring Bean生命周期详解(一)_spring_13


比较重要的过程我都框起来了!

实例化Bean

AbstractAutowireCapableBeanFactory#createBeanInstance(省略了部分不常用的逻辑)

Spring IOC源码解析:Spring Bean生命周期详解(一)_初始化_14


实例化策略如下

  1. 工厂方法不为空则使用工厂方法实例化Bean
  2. 因为Bean的构造函数有可能有很多个,所以要推断使用哪个构造函数来实例化Bean
  3. 如果推断出来的构造函数不为空,则使用推断出来的构造函数实例化Bean,否则使用默认构造函数实例化Bean

使用默认推断出来的构造函数还是使用默认构造函数实例化Bean会缓存下来,下次再实例化的时候就可以直接用,不用再次推断了

属性赋值

AbstractAutowireCapableBeanFactory#populateBean

Spring IOC源码解析:Spring Bean生命周期详解(一)_java_15


属性赋值主要分为属性赋值前阶段和属性赋值阶段

初始化

AbstractAutowireCapableBeanFactory#initializeBean

Spring IOC源码解析:Spring Bean生命周期详解(一)_spring_16


AbstractAutowireCapableBeanFactory#invokeAwareMethods

Spring IOC源码解析:Spring Bean生命周期详解(一)_初始化_17


回调BeanNameAware,BeanClassLoaderAware,BeanFactoryAware接口的注入方法

Spring IOC源码解析:Spring Bean生命周期详解(一)_初始化_18


执行InitializingBean#afterPropertiesSet方法
执行用户自定义的初始化方法,例如@Bean(initMethod = “customerInit”)

注册DisposableBean

当我们想在Bean销毁前做一些操作时,可以通过如下3种方式实现

  1. 使用@PreDestroy注解
  2. 实现DisposableBean接口,重写destroy方法
  3. 自定义销毁方法,例如 @Bean(destroyMethod = “customerDestroy”)

Spring IOC源码解析:Spring Bean生命周期详解(一)_初始化_19


Spring IOC源码解析:Spring Bean生命周期详解(一)_java_20


AbstractBeanFactory#registerDisposableBeanIfNecessary

Spring IOC源码解析:Spring Bean生命周期详解(一)_初始化_21


registerDisposableBeanIfNecessary的作用就是把实现了Bean销毁方法的Bean(以上三种方式只要实现了一种就行)注册到DefaultSingletonBeanRegistry的disposableBeans中

// DefaultSingletonBeanRegistry
/** Disposable bean instances: bean name to disposable instance. */
private final Map<String, Object> disposableBeans = new LinkedHashMap<>();

当容器关闭的时候,就会从disposableBeans拿到需要执行销毁方法的Bean,然后执行对应的销毁方法,执行的优先级为@PreDestroy > DisposableBean > 自定义销毁方法

参考博客

[1]


举报

相关推荐

0 条评论