如何将我的数据库上下文注入我的所有存储库类

时间:2012-10-04 21:13:55

标签: c# asp.net asp.net-mvc-3 ninject

我的每个存储库类都如下所示:

public class ProfileRepository : IProfileRepository{

   private MyEntities myEnt = new MyEntities();
   ...

}

我正在注入我的存储库类:

private static void RegisterServices(IKernel kernel)
        {
            kernel.Bind<IProfileRepository>().To<ProfileRepository>();
            ....
            GlobalHost.DependencyResolver =  new NinjectDependencyResolver(kernel);
            GlobalHost.DependencyResolver.Register(typeof(IConnectionIdGenerator), () => new MyConnectionFactory());
            RouteTable.Routes.MapHubs(new NinjectDependencyResolver(kernel));
        }       

我想将MyEntities上下文注入我的所有存储库类中,因此我在每个存储库类中都没有它的实例。我该如何做到这一点?这会是一种更好的做法吗?

2 个答案:

答案 0 :(得分:3)

首先,您最好使用Ninject.MVC3包。它将为您节省将Ninject附加到框架中的负担,并且只会让您担心绑定。

然后你可以使用    kernel.Bind<your-database-context>().ToSelf().InRequestScope()

如果在同一个MVC请求中创建它们,这将确保所有存储库都将获得相同的DbContext。

注意:如果没有Ninject.MVC3,则不能使用InRequestScope()。

那就是说,我认为存储库是一个绝对可怕的抽象。您需要经历许多环节以抽象出您的数据访问,仅用于单元测试。你最好不要抽象出你的数据访问(微软已经用Entity Framework做了很好的工作),并为你的单元测试准备了一个不错的数据库副本。 Django为单元测试做了类似的工作,我想知道是否有一个单元测试系统可以自动处理(包括应用比单元测试只有数据库快照更新的迁移)。

答案 1 :(得分:3)

我通过创建通用接口(即IMyEntitiesContext)来实现这一目标。

现在,我现在正在记忆中写这个,所以这可能是也可能不是100%正确:

这样的事情:

public interface IMyEntitiesContext : IDisposable
{
    IDbSet<Profile> Profiles { get; }
    ...
    ...
    int SaveChanges();
}

然后,更改您的DbContext类以实现此接口:

public MyEntities : DbContext, IMyEntitiesContext
{
    public IDbSet<Profile> Profiles { get; set; }
    ...
    ...
}

现在,您可以使用IMyEntitiesContext设置构造函数/属性注入:

public ProfileRepository : IProfileRepository
{
    private IMyEntitiesContext _ctx;

    public ProfileRepository(IMyEntitiesContext ctx)
    {
        _ctx = ctx;
    }
}