工厂中的依赖注入

Mát*_*ond 5 php oop factory dependency-injection

我是DI的新手,但我真的很想尝试使用它.

有些事情我不明白.这是一个简单的工厂伪代码,我使用了很多.

class PageFactory {
   public function __construct(/* dependency list */) {
      ... //save reference to the dependencies
   }

   public function createPage($pagename) {
       switch ($pagename) {
           case HomePage::name:
               return new HomePage(/* dependency list */);
           case ContactPage::name:
               return new ContactPage(/* dependency list */);
           ...
           default:
               return null;
       }
   }
}
Run Code Online (Sandbox Code Playgroud)

它有一个非常简单的逻辑,它选择基于字符串的实现实例.它非常有用,因为我可以在以后选择我需要的页面,并且只会创建一个页面.

我将如何重写此代码,因此我的页面实例将由依赖项容器创建,因此我不需要处理工厂及其创建的页面的依赖项?

我看到的唯一解决方案是制作我想要使用的容器,工厂的依赖项,并在工厂内调用它.我有很多问题.

首先,我不想将容器连接到我的应用程序,以及它拥有的每个工厂.

第二,我最大的问题是,对容器的调用非常麻烦,它是字符串式的(即$ container-> get('Foo');).我想尽可能少地使用它.只有一次可能.

编辑:

我不想写一个DI容器.我想使用现有的.我的问题是关于使用情况.我将如何使用DI容器代替或在上述工厂中使用DI容器,同时保持实例选择的逻辑.

编辑2:

我开始使用Dice作为DI容器,因为它很轻,并且知道我需要的一切.如果我可以在一个地方使用它并构建整个应用程序,我更愿意.为此,我需要一种方法以某种方式摆脱这些工厂,或以某种方式修改它以使这些页面像依赖项一样,因此DI容器将为它们提供实例.

编辑3:

是的,我需要这个用于测试目的.我也是测试的新手,但到目前为止我非常喜欢它.

这些页面是MVC框架调用控制器的.但是我检查的所有MVC框架都没有让它们的控制器可测试,因为它们会自动创建它们的实例.并且因为它们是由系统创建的,所以用户无法自定义其构造函数参数.

有一种简单的方法可以检查任何框架.我只是查看我应该在该特定框架中的控制器中使用数据库的方式.大多数框架都是程序性的,或者使用一些服务定位器,无论哪种方式,它们都是从公共范围获取它们的依赖关系,这是我不想做的事情.这就是我没有自动化控制器实例化的原因.缺点是我现在拥有这些奇怪的工厂,它们具有很多依赖性.我想将此任务替换为DI容器.

大多数框架都实现了自己的测试机制,这更像是功能测试,而不是单元测试,但我也不想这样做.

ter*_*ško 3

注意:依赖注入是一种设计模式,而 DI 容器是库,它们通过利用依赖注入来生成实例……或者它们是糟糕的服务定位器,有人将其作为最新的流行事物出售

正确实施的 DI 容器基本上是一个“智能工厂”。但实施一项可能会远远超出您当前的能力。这确实有点复杂,因为一个好的 DI 容器构建整个依赖关系树。

例如:

假设您有一个Foo需要 实例AlphaBeta传入构造的类。但有一个问题。的实例Beta还需要在构造函数中提供一个 PDO DSN 和一个 的实例Cache

一个制作精良的 DI 容器将能够立即构建整个依赖关系树。

您应该使用现有的 DI 容器,而不是自己制作一个。

我的推荐是Auryn