Asp.net mvc 如何解决多层构造函数注入问题
在我的项目中,我对IRepositoryProvider有一个控制器依赖性Asp.net mvc 如何解决多层构造函数注入问题,asp.net-mvc,asp.net-mvc-3,ninject,Asp.net Mvc,Asp.net Mvc 3,Ninject,在我的项目中,我对IRepositoryProvider有一个控制器依赖性 public class HomeController : BaseController { public HomeController(ISessionWrapper sessionWrapper, IRepositoryProvider repositoryProvider, IApplicationCon
public class HomeController : BaseController
{
public HomeController(ISessionWrapper sessionWrapper,
IRepositoryProvider repositoryProvider,
IApplicationConfiguration applicationConfiguration)
: base(sessionWrapper, repositoryProvider, applicationConfiguration)
{}
...
}
IRepositoryProvider及其实现位于BLL层中。另一件需要注意的事情是,IRepositoryProvider也有一些参数。这些用于确定要使用的连接字符串(环境*5个可能的连接)
这一切都适用于两个层和这个Ninject配置
kernel.Bind<IRepositoryProvider>()
.To<RepositoryProvider>()
.InRequestScope()
.WithConstructorArgument("environment",
context => context.Kernel.Get<ISessionWrapper>().CurrentEnvironment)
.WithConstructorArgument("applicationConfiguration",
context => context.Kernel.Get<IApplicationConfiguration>());
所以我的问题是:我是否可以不引用MVC项目中的服务层和BLL层?或者整个设置是一个巨大的代码气味
谢谢
更新:我想我应该说我的理想推荐人。Web->Service->BLL。目前,Web同时引用服务和BLL,以便Ninject解决所有问题
更新2:这似乎是一个可能的解决方案吗 这就是我通常根据需求构建MVC项目的方式 表示层>服务层>业务层>数据访问层 表示层包含:视图模型、视图、控制器。(参考服务层Ninject ddl) 服务层:WCF。(参考BAL等) 业务层:包含我所称的编排器及其接口(引用DAL、域) 数据访问层:包含存储库及其接口(引用域) 域:包含POCO对象 Core:我实际安装和配置Ninject的地方(参考BAL、DAL等) 要将Ninject添加到演示层以外的其他项目,请执行以下操作: 将以下内容添加到Global.Asasx.cs:
DependencyResolver.SetResolver(new NinjectDependencyResolver());
然后创建一个新的项目sucche作为核心。在那里安装Ninject并添加以下类:
您需要从表示层引用Ninject dll
public class NinjectDependencyResolver : IDependencyResolver {
private IKernel kernel;
public NinjectDependencyResolver()
{
kernel = new StandardKernel();
AddBindings();
}
public object GetService(Type serviceType)
{
return kernel.TryGet(serviceType);
}
public IEnumerable<object> GetServices(Type serviceType)
{
return kernel.GetAll(serviceType);
}
public IBindingToSyntax<T> Bind<T>()
{
return kernel.Bind<T>();
}
public IKernel Kernel
{
get { return kernel; }
}
private void AddBindings()
{
//Add your Bindings here
}
}
公共类NinjectDependencyResolver:IDependencyResolver{
私有IKernel内核;
公共NinjectDependencyResolver()
{
内核=新的标准内核();
AddBindings();
}
公共对象GetService(类型serviceType)
{
返回kernel.TryGet(serviceType);
}
公共IEnumerable GetServices(类型serviceType)
{
返回kernel.GetAll(serviceType);
}
公共IBindingToSyntax绑定()
{
返回kernel.Bind();
}
公共IKernel核
{
获取{返回内核;}
}
私有void AddBindings()
{
//在此处添加绑定
}
}
IRepositoryProvider及其实现位于BLL层中。。。
我是否可以不同时引用服务层和BLL层
来自MVC项目
对于你的这两个陈述,答案是否,你不可能“不”引用这些层。最小化引用的最佳方法是将接口与实现分离。例如,您可以具有以下内容:
域层包含您的POCO和接口
- 产品(示例类)
- IRepository(接口)
- 参考
层域
- 实现
(例如IRepository
)ProductRepository:IRepository
- 同时了解
和域
层服务
- 参考
层了解POCO和存储库签名域
- 有一个对
层的引用,但不知道它到底是如何定义的 作品所以,您可以在以后交换DI框架,而一切都将继续工作DI
可以根据需要扩展该层。您可以在
域
和服务
层之间插入BLL
层,您不需要在任何地方引用它。您仍然会使用BLL中定义的IRepositoryProvider,不是吗?所以我想你还是需要引用它。但我不知道Ninject与它有什么关系。ISessionWrapper的实现在一些控制器的不同位置使用。我认为IApplicationConfiguration可以被删除,因为它只在控制器中使用了1到2次,我不知道这两种配置与我的要求有什么关系。所以它在控制器和存储库中都有使用?哪些?ISessionWrapper仅在Web层中使用,但它包含当前选定的环境,需要知道要使用哪些连接。IApplicationConfiguration用于检索正确的连接字符串以及其他一些web.config设置(如允许的广告组、可用环境等)。只需阅读von d.的响应即可。对我在不同的项目中安装和配置ninject。并且只有从表示层到ninject ddl的引用。我这里没有一个示例项目,但是如果你能等的话,我可以在今天晚些时候把它放到github上。我在github上放了一个示例项目。查找Flaviacariica\Registration您的意思是MVC只引用服务层而不是域吗?据我所见,Ninject仍然需要了解这两种类型(接口和具体)。我对关于模块和Ninject的使用的问题进行了编辑。Inject需要知道这两个都是正确的,因为了解它是Ninject的工作。它将创建对象,而不是MVC项目。所以Ninject需要知道一切,MVC只需要知道域(以及签名/接口)。我的观点是,如果Ninject需要同时知道这两个层,那么这两个层都需要被引用。啊,我想我知道混淆的地方。您没有提到在哪里进行Ninject配置。我认为您在MVC中有它,这就是为什么您认为这两个项目仍然需要在MVC中引用。我
DependencyResolver.SetResolver(new NinjectDependencyResolver());
public class NinjectDependencyResolver : IDependencyResolver {
private IKernel kernel;
public NinjectDependencyResolver()
{
kernel = new StandardKernel();
AddBindings();
}
public object GetService(Type serviceType)
{
return kernel.TryGet(serviceType);
}
public IEnumerable<object> GetServices(Type serviceType)
{
return kernel.GetAll(serviceType);
}
public IBindingToSyntax<T> Bind<T>()
{
return kernel.Bind<T>();
}
public IKernel Kernel
{
get { return kernel; }
}
private void AddBindings()
{
//Add your Bindings here
}
}