【发布时间】:2013-08-14 17:35:23
【问题描述】:
我们有一个用 ASP.NET MVC 编写的项目,我们使用 NInject 将存储库注入到控制器中。目前我们正在使用属性和 Inject-attribute 来注入存储库,效果很好:
[Inject]
public IMyRepository MyRepos {get;set;}
另一种注入方式是使用NInjectServiceLocator“手动”进行注入:
var myRepos = NInjectServiceLocatorInstance.Resolve<IMyRepository>();
现在我想知道以下几点:第一种方法要求所有存储库都列在控制器的顶部(当然不一定在顶部,但它是最合乎逻辑的位置)。每当发出请求时,NInject 都会实例化每个存储库。无论在特定操作中是否确实需要所有存储库,都会发生这种情况。
使用第二种方法,您可以更精确地控制实际需要哪些存储库,因此这可能会在创建控制器时节省一些开销。但您可能还必须包含代码以在多个位置检索相同的存储库。
那么哪一个会更好呢?是只拥有一堆存储库属性更好,还是在需要它们的时间和地点解决特定操作实际必需的存储库更好?注入“无用”存储库是否涉及性能损失?那里有(甚至;-)更好的解决方案吗?
【问题讨论】:
-
调用
NInjectServiceLocatorInstance.Resolve是一种称为服务定位器的模式。在 Stackoverflow 和互联网上已经写了很多关于这个的文章(例如这是一个famous article)。 -
@Steven:我知道这种模式,而且它也有它的优点和缺点。正如我所说,使用服务定位器可能仍然不是最好的解决方案,但在这种情况下它会比属性或构造函数注入更好吗?
-
这是你应该进行注入的顺序:构造函数注入、属性注入、工厂、方法注入、服务定位器。仅当上一个选项不合适时才选择下一个选项。
-
@Steven 定义“适当”。当特定操作只使用一个时,在构造函数中定义五个存储库会更好吗?或者更好(也许从性能的角度来看,也许从可读性的角度来看)使用服务定位器并向 NInject 询问实际需要的所需存储库?
-
“合适”的意思是:如果你能做到,你就应该做到!注入在运行时并不总是使用的服务应该不是问题,因为对象图的构建应该非常快(这意味着:除了存储引用之外,不要在构造函数中做任何事情)。如果注入超过 5 个依赖项,则可能违反了单一职责原则。这将导致维护问题。如果你需要延迟类型的创建,你不能使用ctor和prop注入,但你不应该使用服务定位器,因为你可以使用工厂。
标签: asp.net-mvc ninject