使用 servicelocation 而不是构造函数注入来避免编写工厂类的负载是否不好 [英] Is it bad to use servicelocation instead of constructor injection to avoid writing loads of factory classes

查看:17
本文介绍了使用 servicelocation 而不是构造函数注入来避免编写工厂类的负载是否不好的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

现在我们使用 DI/IOC,当我们需要将额外的参数传递给构造函数时,我们使用工厂类,例如

Right now we use DI/IOC and when we need to pass extra parameters to a constructor we use a factory class e.g.

public class EmailSender 
{
    internal EmailSender(string toEmail, string subject,String body, ILogger emailLogger)
    {.....} 
}

public class EmailSenderFactory
{
    ILogger emailLogger;
    public EmailSenderFactory(ILogger emailLogger)
    { 
        this.emailLogger = emailLogger;
    }
    public EmailSender Create(string toEmail, string subject, string body) 
    {
        return new EmailSender(toEmail, subject, body, emailLogger);
    }
}

现在的问题是我们最终创建了一个完整的lotta工厂类,而人们并不总是知道使用它们(他们有时会自己更新它们).像这样编码类的最大缺点是什么:

Now the problem with this is that we end up creating a whole lotta factory classes, and people don't always know to use them (they sometimes new them up themselves). What are the biggest negatives of coding the class like this:

public class EmailSender 
{
    EmailLogger logger = IoC.Resolve<ILogger>();
    internal EmailSender(string toEmail, string subject,String body)
    {.....} 
}

Pro:我们现在可以安全地使用构造函数而无需工厂类缺点:我们必须引用服务定位器(我不担心可测试性,使用模拟容器作为容器的后备服务很容易).

Pro: we now can use the constructor safely without needing a factory class Con: we have to reference the Service Locator (I'm not worried about testability, its easy to use a mock container as the backing service for the container).

我们不应该这样做的原因是否有一些令人讨厌的地方?

Is there some big stinker of a reason out there why we shouldn't do this?

经过深思熟虑,我认为通过拥有一个私有构造函数,并通过嵌套工厂类,我可以将实现和工厂保持在一起,并防止人们不正确地创建类,所以问题已经变得有些无意义了.所有关于 SL 脏的观点当然都是正确的,所以下面的解决方案让我很高兴:

public class EmailSender 
{
    public class Factory
    {
        ILogger emailLogger;
        public Factory(ILogger emailLogger)
        { 
            this.emailLogger = emailLogger;
        }
        public EmailSender Create(string toEmail, string subject, string body) 
        {
            return new EmailSender(toEmail, subject, body, emailLogger);
        }
    }
    private EmailSender(string toEmail, string subject,String body, ILogger emailLogger)
    {
    } 
}

推荐答案

是的 - 很糟糕.

  • 当您可以让框架完成工作时,为什么还要编写所有这些代码?所有 IoC.Resolve() 调用都是多余的,你不应该写下来.
  • 另一个更重要的方面,是你的组件被绑定到您的服务定位器.

  • Why write all that code when you can have the framework do the work? All the IoC.Resolve() calls are superfluous and you shouldn't have to write them.
  • Another, even more important aspect, is that your components are tied to your service locator.

您现在无法实例化它们就像那样 - 你需要一个完全设置服务定位器每次需要使用的地方组件.

You're now unable to instantiate them just like that - you need a completely set up service locator in place every time you need to use a component.

这篇关于使用 servicelocation 而不是构造函数注入来避免编写工厂类的负载是否不好的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆