在没有Unity. mvc的情况下解决Unity依赖
本文关键字:Unity 情况下 解决 依赖 mvc | 更新日期: 2023-09-27 18:16:56
我有两个使用以下Unity逻辑的项目:
container.RegisterType<IUnitOfWork, MyDbContext>(
new HierarchicalLifetimeManager(),
new InjectionFactory(
c => new MyDbContext(configurationService.MySqlConnectionString)
)
);
container.RegisterType<DbContext, MyDbContext>(
new HierarchicalLifetimeManager()
);
第一个项目是一个使用Unity的web应用程序。MVC4包所以有一个定制的DependencyResolver做一些工作- 这个工作很完美。
第二个是一个非web应用程序,所以使用一个正常的Unity包实例,但是当调用使用MyDbContext时出错。例外是
System.Data.Entity.Core。MetadataException:指定的架构不是有效的。错误:entitydatmodel . myproject .ssdl(2,2):错误0152实体框架提供程序类型"System.Data.Entity.SqlServer.SqlProviderServices,EntityFramework。SqlServer, Version=6.0.0.0, Culture=neutral,PublicKeyToken=b77a5c561934e089' for 'System.Data.SqlClient'ADO。NET提供程序无法加载。确保提供程序集对正在运行的应用程序可用。看到网址:http://go.microsoft.com/fwlink/?LinkId=260882
我设置了两个项目调用相同的服务,这是在一个单独的项目中,试图将问题的来源隔离到第二个项目的Unity逻辑。我还应该注意到我使用实体框架6作为ORM。
我的问题是我需要什么Unity代码才能让第二个项目工作,或者是否有一些app.config条目我可以添加以引用EF程序集?
更新:经过一些额外的工作,我注意到如果我引用DbContext程序集:
- EntityFramework
- EntityFramework。
问题消失了。我想避免引用这些程序集,因为我的客户端项目不应该有任何ORM的知识。
我还尝试更新连接字符串,所以我手动指定ORM项目的程序集(我的EDMX文件所在的地方),如这个StackOverflow问题中提到的,但这没有任何区别。
元数据= res://nameOfDll/Model.csdl | res://nameOfDll/Model.ssdl | res://nameOfDll/Model.msl
你这样做是对的。
使用DI,你可以从应用中移除依赖项。这样你就可以得到一个"与存储库无关"的应用程序。你已经有效地做到了。至少在那些"声明"了依赖关系的项目上是这样。然而,当应用程序必须运行时,你需要指定将用于"声明的"抽象依赖(接口,抽象类)所需的具体对象。
通过注册每个抽象依赖项将使用的对象的类型来实现。在您的示例中,当IUnitOfWork
或DbContext
时,提供了MyDbContext
的实例。
因此,"声明"依赖关系的项目完全独立于特定的实现。
然而,当你注册依赖类型时,你就失去了独立性。
让我们看一个例子:
如果我说"我渴了,我需要喝水,但我不介意我喝什么",我依赖于任何饮料,而不是特定的一种。但是如果我说"当我口渴的时候我想喝可乐",我就依赖可乐了。
第一部分是依赖关系的抽象定义:"任意饮料"(如抽象的IUnitOfWork
或DbContext
)。第二部分是具体依赖:"coke"(如MyDbContext
)。
所以,只要我不指定我想喝什么,我就独立于可乐。但是一旦我说了,我就依赖了。
也许你正在寻找一种在运行时更改存储库的方法。您可以这样做:不要在代码中注册依赖项,因为您需要使用所选的具体类型对项目进行引用。在外部配置(即文件)中进行,这样您就可以在不引用依赖项的情况下编译项目,并在运行时提供所需的程序集。
注意:当我说"声明"时,我的意思是使用任何注入依赖的模式,如构造函数注入(大多数建议)或任何其他注入模式(属性依赖)。