使用WithConstructorArgument并创建绑定类型

Eri*_*sch 0 ninject ninject-2

我有一个看起来像这样的绑定:

kernel.Bind<IRepository<Holiday>>().To<RepositoryBase<Holiday>>();
Run Code Online (Sandbox Code Playgroud)

问题是RepositoryBase采用了一个名为context的UnitOfWork的构造函数参数.这不是,本身就是一个问题.Ninject应该解决它.除了我有两个UnitOfWork实现的事实,两个都使用属性鉴别器绑定.

kernel.Bind<IUnitOfWork>().To<MS_DevEntities>().WhenTargetHas<MsDataAttribute>()
    .InRequestScope();
Run Code Online (Sandbox Code Playgroud)

如何指定在创建IRepository时,应该使用MS_DevEntities创建?

当然,我可以这样做:

kernel.Bind<IRepository<Holiday>>().To<RepositoryBase<Holiday>>()
    .WithConstructorArgument("context", new MS_DevEntities());
Run Code Online (Sandbox Code Playgroud)

但是,我宁愿让Ninject创建实例,特别是因为我正在使用.InRequestScope()生命周期.

有什么建议?

编辑:

以前,我使用的是如下所示的类:

public class HolidayRepository : RepositoryBase<Holiday>, IHolidayRepository
{
    public HolidayRepository([MsData]IUnitOfWork context) : base(context){}
}
Run Code Online (Sandbox Code Playgroud)

但是,我现在发现自己有几十个,但是当我需要创建一个新的存储库时,它们并没有做太多工作,而是增加了额外的工作.我想直接在绑定中映射这些.

EDIT2:

我想我可以做这样的事情,但看起来有点像黑客.有没有更好的办法?

kernel.Bind<MS_DevEntities>().ToSelf().InRequestScope();
kernel.Bind<IRepository<Holiday>>().To<RepositoryBase<Holiday>>()
    .WithConstructorArgument("context", 
        (context) => context.Kernel.Get<MS_DevEntities>());
Run Code Online (Sandbox Code Playgroud)

Rem*_*oor 5

例如,将属性放入实体并使用以下内容:

kernel.Bind(typeof(IRepository<>)).To(typeof(RepositoryBase<>));
kernel.Bind<IUnitOfWork>().To<MS_DevEntities>()
      .When(r => EntityHas<MsData>(r));
kernel.Bind<IUnitOfWork>().To<TheOtherOne_DevEntities>()
      .When(r => EntityHas<TheOtherData>(r));

bool EntityHas<TAttribute>(IRequest r)
{
    return r.Target.Member.ReflectedType.IsGenericType &&
           r.Target.Member.ReflectedType.GetGenericArguments()[0]
               .GetCustomAttributes(typeof(TAttribute), false).Any();
}
Run Code Online (Sandbox Code Playgroud)

您可以使用此When条件执行所有操作,并从实体类型r.Target.Member.ReflectedType.GetGenericArguments()[0]中查找您必须用于此实体类型的UoW.

使用config的第二个approch

kernel.Bind<IUnitOfWork>().To<TheOtherOne_DevEntities>()
      .When(r => EntityNeedsUoW(r, 1));

bool EntityNeedsUoW(IRequest r, int id)
{
    return UoWConfig.GetDbIdForEntity(
         r.Target.Member.ReflectedType.GetGenericArguments()[0]) == id;
}
Run Code Online (Sandbox Code Playgroud)