这个代码设计不好,还有什么选择

时间:2015-02-04 11:10:07

标签: unit-testing inversion-of-control solid-principles

我最近实现了一些类似于下面的代码并提交了一个pull请求,以将其添加到我们的共享存储库中。该请求被拒绝,我被告知这种模式很糟糕。相反,我应该让我的依赖项更接近于我的对象的创建。如果父对象创建了一个子对象,那么应该传入一个Func childFactory而不是一个更通用的对象,因为它可能被误用,增加耦合并变得更难测试。

public interface ILogResolverService
{
    ILogger<T> Resolve<T>();
}

public class LogResolverService : ILogResolverService
{
    private readonly IContainer _container;

    public LogResolverService(IContainer container)
    {
        _container = container;
    }

    public ILogger<T> Resolve<T>()
    {
        return _container.Resolve<ILogger<T>>();
    }
}

代码的想法是传递一个可以创建ILogger的对象,以便您可以使用正确的类名进行记录。例如,如果您创建一个子视图模型,您可以让它创建自己的ILogger等

由于这个问题在我的同事们之间存在两极分化,我希望得到社区的意见。

在评论后添加

我应该补充一点,我不认为这是一个ServiceLocator模式,因为它是一个传递给父类构造函数的强类型接口。所以你事先了解所有的依赖关系。可能发生的更糟糕的是将新方法添加到ILogResolverService接口。除非我遗漏了什么。

1 个答案:

答案 0 :(得分:0)

对于我上面概述的设计,我的主要问题是您的服务有点容器感知

即使你证明的返回值是强类型而且明确的是,棘手的部分也在其他地方。领域知识过于宽泛,与容器工作重叠。

通过添加方法显式提供构建器正在使用的依赖关系始终是一个好习惯。

public AddLoggerService[...]

根据您的上下文,您可以通过添加所有需要的依赖运行时来让容器装饰/编译此类服务。

希望我对此事有所了解,

问候。