【问题标题】:IoC and Dependency injectionIoC 和依赖注入
【发布时间】:2013-03-03 17:29:02
【问题描述】:

下面的代码有什么问题?

public class DeDoper {
    public boolean wackapediaOkToday() {
        DnsResolver resolver =  ResolverFactory.getInstance().makeResolver();
        return resolver.getIpAddressFor("wackapedia.org").equals("123.456.78.9");
    }
}

为什么首选这个版本?

public class DeDoper {
    @InjectService
    private DnsResolver resolver;
    
    public boolean wackapediaOkToday() {
        return resolver.getIpAddressFor("wackapedia.org").equals("123.456.78.9");
    }
}

我可以轻松地模拟 ResolverFactory.makeResolver(),这与设置解析器是最新的示例相同。

这是来自 ProQuest.biz 的this article 中所说的:

这个 [第一个] 版本的 WackapediaOkToday 很笼统地说,是“注入”了一个 DnsResolver(尽管它确实不像打针,而更像是向服务员索要支票)。但它确实解决了测试问题,以及“一路乌龟”的问题。

链接到工厂 但是在这个[第一个版本]方法中,我们实际上是“链接”到工厂类的。 (更糟糕的是,如果我们的工厂创建的对象依次具有依赖关系,我们可能不得不在工厂内部引入新工厂。)我们还没有完全“反转”我们的控制,我们仍然从内部调用(控制)工厂我们的班级。

我们需要一种方法来完全摆脱我们类中的控制,并让他们告诉他们得到了什么(对于他们的依赖关系)。

【问题讨论】:

    标签: java jakarta-ee dependency-injection inversion-of-control


    【解决方案1】:

    假设您有一个可以有多个实现的服务,例如“FileLocator”。这有一个 FilesystemFileLocator,它将文件根目录的路径作为参数,还有一个 S3FileLocator,它将您的 S3 凭据作为参数。前者需要你编写一个服务定位器来确定你想要哪个版本,然后返回它。反过来,该代码必须获取您的数据,构建适当类型的文件定位器等。您正在做 IOC 容器应该为您做的事情。最重要的是,您已经注入了对该特定创建方法的依赖。

    在第二个版本中,您已经(通过注释或 XML)定义了您想要的文件定位器类型。 IOC 容器为您实例化和管理它。您必须维护的代码更少。如果要引入第三种类型的 FileLocator,工作量也会减少。或者也许你重构你的代码,使文件定位器是单例的,或者如果它们是单例的,它们现在是新定位器的工厂,或者你可能想要合并定位器实例。在所有这些情况下,如果您使用 IOC 容器,破损将更少。

    【讨论】:

      猜你喜欢
      • 2011-12-12
      • 1970-01-01
      • 2016-07-19
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2016-11-13
      • 1970-01-01
      相关资源
      最近更新 更多