【问题标题】:How is dependency injection working?依赖注入是如何工作的?
【发布时间】:2012-03-16 09:12:06
【问题描述】:

我正在阅读 Pro Spring 2.5 书,我对依赖注入的工作原理有疑问。

我了解 BeanFactory 并进行依赖项查找。现在我读到了依赖注入,我有一些问题。根据我的理解,您希望将查找限制在最低限度,例如查找用于引导应用程序的对象。然后依赖注入将负责其余的工作。但是我不明白这行得通。

假设您有一个 beanfactory,您将获得一个启动整个应用程序的 MyApplication 实例。其余的对象使用依赖注入来获取它们的协作者。 beanfactory 维护它管理的 bean 列表,但这个工厂不是仅在应用程序的 main 方法中可用吗?如果 beanfactory 还管理其包含的 bean 的范围,我不明白这是如何完成的。 beanfactory 在某种程度上是全球性的吗?

【问题讨论】:

    标签: java spring dependency-injection


    【解决方案1】:

    bean 工厂实例化所有对象。它解析您的配置(xml 或注释),实例化您的 bean 并设置它们的依赖关系。然后所有这些 bean 都存储在应用程序上下文中。

    您的应用程序通常有一个入口点 - 您在那里有 context.getBean(..)。现在该 bean 已注入其依赖项,因为它是由 bean 工厂放入上下文中的。

    经验法则可能会让事情变得清晰:在使用 DI 框架时,永远不要使用 new 运算符(带有 bean 类)。框架生成实例,而不是你。

    【讨论】:

    • 那么“启动”应用程序的 bean 现在有一个寄存器,它可以在其中获取注入其依赖项并准备使用的 bean?
    • 是的。在 web 上下文中,例如上下文(注册表)是由一个监听器启动的,它是由 spring 提供的,你看不到。
    【解决方案2】:

    因此,有两种方式会发生这种情况(从 Spring 3 开始)。在“传统”依赖注入中,bean 工厂只能将依赖注入到它自己创建的 bean 中。在这种情况下,bean 工厂将在第一次创建 bean 时解析并注入 bean 的所有依赖项。

    另一种方式要求您使用“完整的”AspectJ 与加载或编译时编织。在这种情况下,您使用 spring-aspects.jar 中的一个切面,它基本上切入所有new 操作,允许您在任意创建的对象中获得依赖注入。这是通过使用 @Configurable 注释触发的。你可以阅读更多here

    【讨论】:

      【解决方案3】:

      控制反转和依赖注入的全部意义在于您(通常)不需要 beanfactory,除了启动您的应用程序。您的依赖项“自动出现”在您的对象中。这基本上适用于在您的应用程序的整个生命周期中具有很少(通常是一个)实例的对象。

      例如如果你的 MyApplication 依赖于 MyModuleA 的一个实例,你可以简单地拥有它@Autowired。当您在启动时从 beanfactory 获取应用程序对象时,它已经带有 MyModuleA 预设的实例。

      关于范围:这来自网络上下文。除了只有一个实例的对象之外,您还可以将对象范围限定为用户会话。在那里,您可以存储您需要为多个请求保留但为不同用户分开的信息,例如:购物车。

      通常将 bean 工厂视为全局。我认为可能有多个实例,但它们会断开连接并且不能注入只有其他实例知道的对象。

      【讨论】:

        猜你喜欢
        • 2014-01-09
        • 1970-01-01
        • 2015-06-15
        • 2011-04-13
        • 2021-07-02
        • 1970-01-01
        • 1970-01-01
        • 2017-12-23
        • 2015-11-08
        相关资源
        最近更新 更多