1

我正在使用带有上下文和 ninject 作为 IOC 的存储库模式。我有一项服务可以处理在数据库中获取和设置页面属性。

public class MyContext : DbContext
{
    public MyContext() : base ("DefaultConnection")
    {
    }

    public DbSet<PageProperty> PageProperties { get; set; }
    public DbSet<Contact> Contacts { get; set; }
}

public class DefaultRepository : IRepository
{
    MyContext _context;
    public DefaultRepository(MyContext context)
    {
        _context = context;
    }

    public IQueryable<PageProperty> PageProperties { get { return _context.PageProperties; } }
    public IQueryable<Contact> Contacts { get { return _context.Contacts; } }
}

public class ModuleLoader : NinjectModule
{
    public ModuleLoader()
    {

    }

    public override void Load()
    {
        var context = new MyContext();
        context.Database.Initialize(false);
        Bind<MyContext>().ToConstant(context).InSingletonScope();
        Bind<IRepository>().To<DefaultRepository>();
        Bind<IPagePropertyProvider>().To<DefaultPagePropertyProvider>().InSingletonScope();
    }
}

public class DefaultPagePropertyProvider : IPagePropertyProvider
{
    IRepository _repository;
    object _syncLock = new object();

    public DefaultPagePropertyProvider (IRepository repository)
    {
        _repository = repository;
    }

    public string GetValue(string pageName, string propertyName
    {
        lock (_syncLock)
        {
            var prop = page.PageProperties.FirstOrDefault(x => x.Property.Equals(propertyName) && x.PageName.Equals(pageName)).Value;

            return prop;
        }
     }
     public void SetValue(string pageName, string propertyName, string value)
     {
         var pageProp = _repository.PageProperties.FirstOrDefault(x => x.Property.Equals(propertyName) && x.PageName.Equals(pageName));
         pageProp.Value = value;
         _repository.SaveSingleEntity(pageProp);
     }
}

在我看来,我正在进行 3 次 ajax 调用,一次是从联系人中获取列表以填写表格,一次 ajax 调用以确定我有多少页面,具体取决于我正在使用的页面大小,以及一次 ajax 调用来设置我想使用的页面大小。所以一个选择框会改变页面大小(每页有多少联系人:[30]),一个显示联系人的表(从 jquery 生成,其中 deifers json),最后是一个包含要单击的页码列表的 div。工作流程是,调用GetContacts(),此函数然后查询PageProperties以找出要使用的页面大小,然后调用GetPages(),此函数还查询PageProperties以找出要使用SetPageSize()的页面大小,从而设置页面大小。所以GetContacts()andGetPages()用于从 div 中选择页面时,SetPageSize()然后GetContacts()GetPages()在触发选择框更改事件时调用。GetContacts()并且仅在第一个请求存在并且该函数有 aGetPages()时才调用。SetPageSize() $.ajaxdone()success

现在,在我添加lock(syncLock)DefaultPageProperty服务之前以及在我添加InSingletonScope到该服务和上下文之前,我遇到了两个错误。

连接未关闭。连接的当前状态是正在连接。

一个 EdmType 不能多次映射到 CLR 类

我假设因为连接处于一种connecting状态,上下文正在被重用,重用和重用,所以我认为把它放到SingletonScope()意味着只建立了一个连接,然后我也这么想DefaultPageProperty,然后因为我正在进行异步调用对于该服务,我应该锁定数据库查询。

它有效,并且问题不存在。但我不知道我所做的在我使用的模式中是否正确,我想知道我是否错过了一些基本的东西?我的问题是,这是一个适当/可行的解决方案,以后不会产生任何警告吗?我真的解决了这个问题还是创造了更多?

4

1 回答 1

0

我重新设计了我现在处理上下文的方式。

我有我的上下文,然后我实现IDbContextFactory<TContext>调用DefaultContextFactory<MyContext>并注入它们。

在我在公共构造函数中的存储库中_context = contextFactory.Create();

然后在整个存储库中我只使用_context.WhatEver()它并且它很好。

ModuleLoader Bind<IRepository>().To<DefaultRepository>().InTransientScope()为了让每次调用它都创建一个新的存储库,我也这样做了!

我不需要存储库工厂,因为我只有一个存储库!

于 2013-08-24T15:57:50.027 回答