Jas*_*ung 5 design-patterns dependency-injection inversion-of-control
我使用了大量的依赖注入,但我想在运行时获得有关如何处理用户信息的输入。
我有一个连接到 com 端口的类。我允许用户选择 com 端口号。现在,我将该 com 端口参数作为构造函数参数。原因是该类没有该信息就无法运行,并且它是特定于实现的(此类的模拟版本不需要 com 端口)。
另一种方法是使用一个“Start”方法来接收 com 端口,或者使用一个设置 com 端口的属性。这使得它与 IoC 容器非常兼容,但从类的角度来看它不一定有意义。
看起来逻辑路线与依赖注入设计冲突,但这是因为我的 UI 正在获取特定类型类的信息。
其他替代方法包括使用 IoC 容器,让我传入额外的构造函数参数,或者仅在顶层构造我需要的类而不使用依赖注入。
对于此类问题,是否有普遍接受的标准模式?
根据您的需要,您可以选择两条路线。
这是最简单的选择,但很多时候完全可以接受。虽然您可能有一个具有大量接口和使用 DI 的域模型,但 UI 构成了对象图的组合根,您可以简单地在此处连接您的具体类,包括所需的端口号参数。
好处是这种方法简单且易于理解和实施。
缺点是灵活性较差。您将无法任意地将一种实现替换为另一种实现(但话说回来,您可能不需要这种灵活性)。
即使 UI 锁定到一个具体的实现,这并不意味着域模型本身不能在其他应用程序中重用。
另一种选择是添加另一个间接层。它可以使用抽象工厂来创建实例,而不是让您的 UI 直接创建类。
工厂的Create方法可以将端口号作为输入,因此这种抽象最适合在 UI 子层中使用。
public abstract class MyFactory
{
public abstract IMyInterface Create(int portNumber);
}
Run Code Online (Sandbox Code Playgroud)
然后,您可以让 DI 容器连接该工厂的实现,该工厂使用端口号并将其作为构造函数参数传递给您的实际实现。其他工厂实现可能会简单地忽略该参数。
这种方法的优点是您不会污染您的 API(或您的具体实现),并且您仍然拥有接口编程为您提供的灵活性。
缺点是它增加了另一层间接。