0

我已经完成了一个新应用程序的编写,该应用程序现在已经部署到实时环境中,但是我的全局错误处理程序全天多次处理这些异常。这些错误是分批出现的,是四个粗体错误之一。

MVC 4、IIS 6、Windows Server 2003、.Net .4.0、EF 5(来自 NuGet 的最新版本)

'ARandomModelInMyContext' 类型已被多次映射。

指数超出范围。必须是非负数且小于集合的大小。

Parameter name: index
System.ThrowHelper.ThrowArgumentOutOfRangeException() at System.Data.Metadata.Edm.MetadataCollection`1.get_Item(Int32 index) at System.Data.Mapping.DefaultObjectMappingItemCollection.ContainsMap(GlobalItem cspaceItem, ObjectTypeMapping& map) at

创建模型时不能使用上下文。

System.Data.Entity.Internal.LazyInternalContext.InitializeContext() at System.Data.Entity.Internal.InternalContext.GetEntitySetAndBaseTypeForType(Type entityType) at System.Data.Entity.Internal.Linq.InternalSet`1.Initialize()

基础提供程序在打开时失败。连接未关闭。连接的当前状态是正在连接。

应用程序的结构是一个非常标准的 MVC4 应用程序,具有服务层和存储库层。

  • 服务在构造函数中创建一个 repo
  • 存储库在存储库构造函数中创建一个新的上下文,如下所示:

public class MyRepository : BaseRepository<MyModel>, IMyRepository

使用构造函数:

public MyRepository() : base(new MyEntities())
{
}

基本存储库如下所示:

public class BaseRepository<TEntity> where TEntity : class
{
    internal CRMEntities Context;
    internal DbSet<TEntity> dbSet;
    public BaseRepository(MyEntities context)
    {
        this.Context = context;
        dbSet = context.Set<TEntity>();
    }
}

不应该有任何并发​​问题,因为我没有直接使用任何线程或异步。

有任何想法吗?我的存储库结构可以改进吗?我已经让所有的构造函数都可以 DI,但是我还没有使用 IoC 容器。

将存储库中 Context 的构造锁定是否值得?例如:

public class BaseRepository<TEntity> where TEntity : class
{
    internal MyEntities Context;
    internal DbSet<TEntity> dbSet;
    private static object _lock = new object();

    public BaseRepository(MyEntities context)
    {
        lock (_lock)
        {
            this.Context = context;
            dbSet = context.Set<TEntity>();
        }
    }
 }
4

1 回答 1

1

它看起来非常像您的存储库(以及您的上下文)被多个请求使用。如果这是真的,那么这是对同一上下文实例的多线程使用,这是不受支持的——上下文不是线程安全的。仅锁定初始化是不够的。(此外,调用 Set 不会初始化上下文。)您需要保护对上下文的所有访问,或者更恰当地使用具有短期上下文实例的每个请求模型的上下文。

于 2012-11-07T17:36:15.423 回答