AbstractApplicationContext.refresh()

272 阅读4分钟

prepareRefresh()

  1. 核心描述 - 用来刷新上下文环境的配置信息

  2. 具体执行 initPropertySources() - 初始化系统的配置信息

  3. getEnvironment().validateRequiredProperties() - 验证需要的属性文件是否都已经放入环境中

ConfigurableListableBeanFactory beanFactory = obtainFreshBeanFactory()

  • 核心- 解析xml文件,获取BeanFactory的全部信息

  • 核心 -通过AbstractRefreshableApplicationContext.refreshBeanFactory()方法

    • 将xml文件提供的信息,都放到 DefaultListableBeanFactory 类中

      • 其中DefaultListableBeanFactory中比较重要是

      • Map<String, BeanDefinition> beanDefinitionMap

      • BeanDefinition 类中,是bean的定义。包括(lazyInit ,initMethod 等xml支持的配置信息)

大致的解析过程

  1. XmlBeanDefinitionReader.loadBeanDefinitions() 是入口

  2. XmlBeanDefinitionReader.doLoadDocument () 将xml文件,解析成Doc 信息

  3. XmlBeanDefinitionReader.registerBeanDefinitions() - 提供doc的信息,对bean 的相关属性进行 定义

    1. DefaultBeanDefinitionDocumentReader.registerBeanDefinitions() 方法 - 是入口

    2. DefaultBeanDefinitionDocumentReader.doRegisterBeanDefinitions()方法 - 进行解析doc - Element 的元素

    3. DefaultBeanDefinitionDocumentReader.parseBeanDefinitions() - 进行解析

      1. DefaultBeanDefinitionDocumentReader.parseDefaultElement() 对于默认标签的解析

        • 主要是import、alias、bean、beans的标签解析
      2. DefaultBeanDefinitionDocumentReader.parseCustomElement() 对于自定义标签的解析

        • 可以 自定义 NamespaceHandlerSupport#parse() 进行解析

prepareBeanFactory(beanFactory)

  • 核心 - 是对beanFactory的填充

    • 添加Thread.currentThread().getContextClassLoader() 的类加载器

    • 对EL表达式的解析器支持- "#{...}"

    • 对Bean的属性解析器的支持

    • 可以自定义实现属性解析器

    • 增加对AspectJ的支持

等等

postProcessBeanFactory(beanFactory);

  • 用来给子类实现 - 用来增加 BeanPostProcessor

invokeBeanFactoryPostProcessors(beanFactory);

  • 核心 - 用来对Bean的定义做一些修改。

  • 修改的是bean的BeanDefinition对应的一些信息。

    • 例如 - 原来 A.id = 5 , 可以修改为A.id = 100; 这种
  • 自定义 实现 - 通过继承BeanFactoryPostProcessor类

    • postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) 方法进行对bean的定义进行修改

registerBeanPostProcessors(beanFactory);

  • 核心- 用于对bean对一些修改

  • 例如 自定义 implements BeanPostProcessor

 @Override
    public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
        System.out.println("MyBeanPostProcessor#postProcessBeforeInitialization");
        if (bean instanceof UserService) {
            System.out.println(beanName);
        }
        // 自己的逻辑
        return bean;
    }
 
    @Override
    public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
        System.out.println("MyBeanPostProcessor#postProcessAfterInitialization");
        // 自己的逻辑
        return bean;
    }

initMessageSource();

  • 核心 - 初始不同的Message源,用于国际化信息处理

  • 要是自定义Message。 beanId必须是 messageSource 。代码里面写死了

initApplicationEventMulticaster();

  • 核心 - 初始化广播器

  • 默认使用的是 SimpleApplicationEventMulticaster

onRefresh();

  • 留给子类来初始化其它的bean

registerListeners();

  • 核心在所有注册的Bean中,找监听器

    • ApplicationListener
  • 核心并将监听器,注册到广播器中SimpleApplicationEventMulticaster

  • 可以自定义 详细在看看

finishBeanFactoryInitialization(beanFactory);

  • 核心 - 真正会初始化 xml 文件配置的bean

  • 前提描述

    • BeanFactory - 是存放xml中所有的bean 信息。

    • FactoryBean - 是每个bean都有一个对应的创建bean实现类

    • ObjectFactory - 是每个FactoryBean 都有一个对应的 ObjectFactory

  • 核心类

    • DefaultSingletonBeanRegistry - 保持bean的注册情况

      • 前提描述- 对应bean的加载,Spring分为了三种情况(三级缓存),并分别保持起来。防止循环引用

        • bean已经实例化 - Map<String, Object> singletonObjects - 保存beanName,与Bean具体的实例

        • bean未创建,但有ObjectFactory了。 Map<String, ObjectFactory<?>> singletonFactories

        • bean正在创建(提前) - Map<String, Object> earlySingletonObjects - 保存beanName ,与Bean正在创建,用来检测循环引用(提前曝光已经实例化-但没有填充属性)

  • 解析流程

  1. DefaultListableBeanFactory.preInstantiateSingletons() - 入口

    1. isFactoryBean(beanName) - 对xml文件中bean 进行加载

    2. 获取 bean对应的 FactoryBean

    3. AbstractBeanFactory.doGetBean() - 会真正开始做bean的加载

      1. 首先会尝试从缓存中 (DefaultSingletonBeanRegistry.getSingleton() 方法),直接获取。如果给能够获取ObjectFactory —> FactoryBean -> Bean 最终获取到bean

      2. 如果 DefaultSingletonBeanRegistry.getSingleton() == null,则进行bean的加载

      3. 获取Bean的依赖 mbd.getDependsOn();

      4. 判断bean的创建模式 - mbd.isSingleton() 是否为单例

      5. 调用 DefaultSingletonBeanRegistry.getSingleton(String beanName, ObjectFactory<?> singletonFactory)

        1. 记录bean的加载状态
        2. singletonObject = singletonFactory.getObject(); -- 获取ObjectFactory
      6. 调用AbstractAutowireCapableBeanFactory.createBean() 方法 ,创建bean

        1. AbstractBeanFactory.resolveBeanClass() 方法- 解析bean.class

        2. AbstractAutowireCapableBeanFactory.resolveBeforeInstantiation () - 通过自定义的BeanPostProcessors 来实例化。会调用 before 与after

        3. 若还是没有,则继续执行 AbstractAutowireCapableBeanFactory.doCreateBean() 方法创建bean

          1. AbstractAutowireCapableBeanFactory.createBeanInstance() 方法真正的实例化bean。返回是BeanWrapper的包装类,通过getWrappedInstance()方法,获取到对象

            1. 第一种 如果bean定义中存在 InstanceSupplier ,会使用这个回调接口创建对象 (3.X以后新加的) -- 实现自定义 Supplier

            2. 第二中 通过xml配置的factory-bean factory-method 等创建工厂类的方式来实现

            3. 第三中,通过函数构造器创建 bean 。 采用的是策略模式 来创建

              1. 对于有参数的 - 解析构造器参数放入缓存 - 对于带参数的构造器,要解析参数的个数与类型 -- 此次做了大量操作

                1. 通过反射 或者 cglib 的方式创建对应的bean
              2. 对于无参数的

                1. 通过反射 或者 cglib 的方式创建对应的bean -- BeanUtils.instantiateClass() 方法
          2. DefaultSingletonBeanRegistry.addSingletonFactory() 方法,会将bean的ObjectFactory 加入到

          Map<String, ObjectFactory<?>> singletonFactories
          

          当A 依赖 B ,B依赖A时

          初始A时,A的实例会加入到 singletonFactories

          由于A依赖B,通过👇这个方法,会初始B

          而B依赖A,而A在 singletonFactories 已经存在了。 B可以直接获取 A(没有填充属性的A)这样A 与 B 都初始化成功了

          1. AbstractAutowireCapableBeanFactory.populateBean() 对bean 的属性进行填充
          2. AbstractAutowireCapableBeanFactory.registerDisposableBeanIfNecessary() 根据scpoe进行注册-完成bean的创建

finishRefresh()

  • 核心 - 清除缓存,启动刷新