Spring 5 源码解析- AbstractApplicationContext#refresh()方法解析

spring-framework 启动时,主要逻辑在AbstractApplicationContext#refresh()类中。在类 refresh() 方法中,通过13个特定功能的方法,完成运行上下文(context)的创建。详情如下:

一. prepareRefresh()

   刷新方法之前预处理上下文信息:
   1.记录服务启动是时间戳
   2.设置当前服务 context 关闭标记(closed),活动标记(active)
   3.根据需要执行特殊的属性初始化操作。
   4.校验必须配置属性是否设置成功
   5. 设置早期的事件监听列表 ApplicationListener 列表。

二.  obtainFreshBeanFactory()

   获取 BeanFactory 实例。其中包含 读取 bean 配置,创建bean 实例对象相关代码逻辑。具体再详细分析。

 

三.  prepareBeanFactory(ConfigurableListableBeanFactory beanFactory)

     对获取的 BeanFactory  实例对象进行预处理。

      1.设置 Bean 的类加载器(beanClassLoader)。

      2.根据配置 spring.spel.ignore 添加表达式解析工具类实例(StandardBeanExpressionResolver)。

      3.添加属性编辑器注册器(ResourceEditorRegistrar)。 

      4.添加 Aware 接口执行器(ApplicationContextAwareProcessor),并将 Aware的子接口 接口设置为忽略依赖接口。

      5.注册 指定类型类的实例。BeanFactory.class, beanFactory

      6.添加实现BeanPostProcessor接口的 Listener 装饰器 (ApplicationListenerDetector)。后续将实现 ApplicationListener 的bena添加到 applicationListeners 列表钟。

      7.如果配置了loadTimeWeaver实现,则添加实现BeanPostProcessor接口的 LoadTimeWeaverAwareProcessor。后续给实现LoadTimeWeaverAware 的bean设置LoadTimeWeaver实现对象。

          实际中使用较少。

                  编译期织入:  是指在编译java文件时,使用特殊的编译器编译Java文件,将切面织入到生成的类字节码文件中;
                  类加载期织入(LTW) : 在类加载器加载时,通过字节码编辑技术将切面织入目标类字节码上 。(https://www.jianshu.com/p/25cd25046fab)
                                 类加载期织入有两种方式:一种是在 main 方法执行之前,通过 premain 来实现;另一种是在程序运行中,通过 attach api 来实现。
                  运行期织入:在创建类对象实例时,使用CGLib代理或JDK动态代理进行切面的织入。

       8.将环境变量和系统属性相关的对象实例注册到 单例Bean Map中。
                     getEnvironment().getSystemProperties() JVM 启动时相关的环境属性信息
                     getEnvironment().getSystemEnvironment() OS 系统的环境变量相关属性信息

四.postProcessBeanFactory(beanFactory)

     子类重写此方法进行定制化处理.


五.invokeBeanFactoryPostProcessors(beanFactory)

    回调 BeanFactoryPostProcessors 实现类的postProcessBeanFactory方法,进行BeanFactory后置处理。    

     PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors()

      1. 根据 PriorityOrdered,Ordered以及常规的 BeanDefinitionRegistryPostProcessor 实现类 顺序依次调用 的 postProcessBeanDefinitionRegistry 方法。
      2. 根据 PriorityOrdered,Ordered以及常规的 BeanFactoryPostProcessors 实现类 顺序依次调用 的postProcessBeanFactory方法

六.registerBeanPostProcessors(beanFactory)

    向 BeanFactory 中注册 BeanPostProcessor 实现类。

    PostProcessorRegistrationDelegate.registerBeanPostProcessors
     1.从 BeanFactory 取出 beanDefinitionMap 中所有 BeanPostProcessor 实现类
     2. 按 PriorityOrdered,Ordered以及nonOrdered 顺序添加到 BeanFactory的beanPostProcessors 列表中。
      如果 一个实现类继承 MergedBeanDefinitionPostProcessor 接口时,则添加到列表最后。

 

七. initMessageSource()

     设置 context 消息的国际化实现类。如果没有配置,则使用 DelegatingMessageSource 实现。

八. initApplicationEventMulticaster()

     设置 context 广播器(applicationEventMulticaster)。如果没有配置,则使用 SimpleApplicationEventMulticaster 实现。

九. onRefresh() 

  根据需要,子类自定义 onRefresh()。

 

十. registerListeners()

     注册 Listeners (列表),广播 earlyApplicationEvents 事件。
     1.将 context 的 applicationListeners (列表) 添加到广播器(applicationEventMulticaster)的applicationListeners(列表)中。
     2.将 BeanFactory 中管理的所有 ApplicationListener 类型Bean添加到广播器(applicationEventMulticaster) applicationListenerBeans(列表)中。
     3.将 earlyApplicationEvents 事件列表发送到广播器(applicationEventMulticaster)。将遍历触发满足监听事件的 ApplicationListener.onApplicationEvent 方法。

 

十一. finishBeanFactoryInitialization(beanFactory)

         BeanFactory 最终的初始化操作
           1. beanFactory 设置 ConversionService 实现Bean。
           2. beanFactory 设置 EmbeddedValueResolver 实现Bean。
           3. 获取 beanFactory 所有 LoadTimeWeaverAware 类型 bean。并创建 bean 实例。
           4. beanFactory 设置 tempClassLoader 为 null。阻止再使用 tempClassLoader
           5. beanFactory 冻结配置 beanDefinitionNames。为后面 批量处理单例 Bean 做准备。
           6. beanFactory 获取所有非懒加载的单例 bean对象。

十二. finishRefresh()

        上下文(context) 后续处理逻辑。

         1. 清理资源缓存(resourceCaches)信息
         2. 设置 context 的生命周期处理器 (LifecycleProcessor)。如果没有配置,则使用 DefaultLifecycleProcessor 实现。
         3. 调用 LifecycleProcessor.onRefresh 方法。获取 beanFactory 中所有 Lifecycle 类型bean,按 Phased 分组进行排序,然后遍历执行 Lifecycle.start 方法。
         4. 发布 ContextRefreshedEvent 事件。先向当前上下文(context) 环境发送事件广播。然后向父类发布 ContextRefreshedEvent 事件广播。
         5. 获取 平台 MBeanServer 实现,将 LiveBeansView 和 applicationName 注册到 MBeanServer 中。

 

十三.resetCommonCaches()

      清理公共缓存。

        1.清理反射中缓存的方法和字段信息。

        2.清理注解缓存的信息。

        3.清理解析类型相关的缓存信息。

        4.清理类加载器相关的信息。

 

上一篇:invokeBeanFactoryPostProcessors(beanFactory);


下一篇:beanFactory创建流程 以及BeanDefinition的装填 自定义spring标签