返回

Spring Bean 实例化和 IOC 依赖注入:深入源码分析(二)

见解分享

引言

Spring 框架是当今 Java 开发中广泛采用的依赖注入框架。它通过其 bean 工厂管理 bean 的生命周期,包括实例化和依赖注入。在本文中,我们将深入研究 Spring 框架,具体分析 bean 实例化和 IOC 依赖注入的过程。我们将使用 Spring 5.3.23 版本,并专注于 DefaultListableBeanFactory 的 preInstantiateSingletons() 方法,这是 bean 实例化和依赖注入的关键入口点。

bean 的生命周期

在 Spring 框架中,bean 经历了一个明确的生命周期,包括:

  1. 实例化: 创建 bean 实例。
  2. 属性填充: 填充 bean 的属性值。
  3. 依赖注入: 解析和注入 bean 的依赖项。
  4. 初始化: 执行 bean 的初始化方法。
  5. 销毁: 在 bean 不再需要时销毁它。

DefaultListableBeanFactory.preInstantiateSingletons()

DefaultListableBeanFactory.preInstantiateSingletons() 方法是 bean 实例化和依赖注入过程的入口点。它被调用来预实例化所有单例 bean,以便在需要时快速访问它们。

preInstantiateSingletons() 方法的主要步骤如下:

  1. 获取所有单例 bean 定义: 从 bean 工厂获取所有标记为单例作用域的 bean 定义。
  2. 排序 bean 定义: 根据依赖关系对 bean 定义进行排序,确保依赖 bean 在父 bean 之前实例化。
  3. 实例化 bean: 遍历排序后的 bean 定义并创建它们的实例。
  4. 属性填充: 填充 bean 的属性值。
  5. 依赖注入: 解析和注入 bean 的依赖项。
  6. 初始化 bean: 执行 bean 的初始化方法。

依赖关系解析算法

依赖关系解析是 preInstantiateSingletons() 方法的关键部分。Spring 使用了一种深度优先算法来解析依赖关系:

  1. 获取 bean 的依赖项: 从 bean 定义中获取依赖项列表。
  2. 递归解析依赖项: 对于每个依赖项,递归调用依赖关系解析算法来解析其依赖项。
  3. 检查循环依赖: 在解析过程中,Spring 会检查循环依赖,并抛出异常来防止无限递归。
  4. 实例化和注入: 一旦依赖关系被解析,Spring 将实例化依赖 bean 并将其注入到主 bean 中。

示例代码

为了说明 bean 实例化和依赖注入的过程,让我们考虑以下示例代码:

public class BeanA {
    private BeanB beanB;

    public BeanA(BeanB beanB) {
        this.beanB = beanB;
    }
}

public class BeanB {
    private BeanC beanC;

    public BeanB(BeanC beanC) {
        this.beanC = beanC;
    }
}

public class BeanC {
}

public class App {
    public static void main(String[] args) {
        ApplicationContext context = new AnnotationConfigApplicationContext(AppConfig.class);
        BeanA beanA = context.getBean(BeanA.class);
    }
}

在示例中,BeanA 依赖于 BeanB,BeanB 依赖于 BeanC。当 DefaultListableBeanFactory.preInstantiateSingletons() 方法被调用时,它将按照以下顺序实例化和注入 bean:

  1. BeanC
  2. BeanB
  3. BeanA

Spring 会自动解析依赖关系,并根据给定的构造函数参数注入 bean。

结论

在本文中,我们深入分析了 Spring bean 实例化和 IOC 依赖注入过程。我们重点研究了 DefaultListableBeanFactory.preInstantiateSingletons() 方法,了解了它如何管理 bean 生命周期并解析依赖关系。通过理解这些机制,我们可以更深入地了解 Spring 框架并更有效地构建基于 Spring 的应用程序。