【问题标题】:Is it right to use spring DI without interface不带接口使用spring DI对吗
【发布时间】:2014-12-04 05:50:53
【问题描述】:

我正在使用spring依赖注入,我可以通过一些外部xml文件注入对象依赖。

我的问题是:

不使用接口就可以使用spring DI吗?

因为有了 DI,我们想要实现一件事:

如果一个类被其他具有相同方法但定义不同的类替换,那么我们不需要对引用该类的代码进行任何更改。

如果我使用接口,这很好,因为接口可以指向任何实现此接口的类,但如果我通过 DI 直接注入类对象,那么 DI 没有意义,因为在这种情况下,如果类被替换,我有在引用它的地方更改我的代码。

如果有错误请让我纠正。

假设我有

Class Datasource{

    String url;
    String user;
    String database;

}

现在我在没有 DI 的情况下使用它

Class Abc{

     Datasource datasource = new Datasource();
}

这有什么问题,如果我使用 DI 可以获得什么好处。

获取单例对象只是 DI 的目标吗?

【问题讨论】:

  • 这不是您想要通过依赖注入实现的目标。您希望外部化配置相关对象(即使用存储库的服务)的控制。 DI 与能够替换依赖项无关。无论您是否使用接口,依赖注入都可以并且将会起作用。
  • 我们在 XML 中没有提到接口,而是提到了类。在实时应用程序中,类很少被其他类替换或交换。并且 DI 不是“如果一个类正在重新......”
  • @M.Deinum 如果 DI 不是“如果一个类...”那么 DI 有什么好处,我为什么要外部化控件?
  • 因为您可能希望重用一个对象(单例)或提供实际对象的代理。如果您在另一个对象中实例化对象,您不会得到所有这些。但是,这不是您不想在各处构建对象的主要好处。想象一下需要一个数据源,您可能希望配置一次并让其他类使用它,您不希望每个类都设置一个DataSource
  • @M.Deinum 没有明白你的意思,请查看我的更新

标签: java spring interface dependency-injection


【解决方案1】:

依赖注入与接口、类或枚举无关,或者......它是关于Inversion of Control

想象下面的类。

public class PersonService {

    private PersonRepository repository = new PersonRepository();
}

显然这并没有什么问题。但是,如果PersonRepository 需要其他依赖项怎么办,如果它需要另一个复杂对象作为构造参数怎么办。突然之间,PersonService 就背负着如何构造对象及其所有依赖项的逻辑。而它只想使用对象。

public class PersonService {

    private PersonRepository repository;

    public PersonService() {
         InitialContext ctx = new InitialContext();
         repository = ctx.lookup("java:comp/env/repositories/person");
    }
}

上面的代码与 JNDI 相关联,您将如何(轻松地)测试它?当然,您可以构建自己的 Mock JNDI 服务并使用构建或模拟的存储库预先配置它,但这很麻烦。

 public class PersonService {

      private final PersonRepository repository;
      public PersonService(PersonRepository repository) {
          this.repository=repository;
      }
 }

以上内容基本上使一切成为可能,PersonService 上没有关于如何构造PersonRepository 的负担,它只是交给一个,它来自哪里并不重要。它是实际的类还是(基于类的)代理,不在乎。

因此依赖注入,您想将PersonRepository 交给PersonService 使用,它来自哪里、如何构造或者它是否是实际对象的代理都无关紧要。它只需要一个PersonRepository

【讨论】:

  • 感谢您的回答,这是有道理的,如果创建对象是一个有点复杂的任务,那么应该使用 DI,但我见过很多项目创建对象很简单,比如 new Abc(),仍然有人使用 DI 来注入 Abc。
  • 这不是关于简单性而是关于责任......这不是PersonService 的责任来构造它需要的引用对象。只需将它们交给对象即可。
猜你喜欢
  • 2011-02-20
  • 1970-01-01
  • 1970-01-01
  • 2021-08-25
  • 2020-02-24
  • 1970-01-01
  • 1970-01-01
  • 2014-05-06
  • 2018-01-25
相关资源
最近更新 更多