简体   繁体   English

创建ThreadLocal EF上下文

[英]Creating a ThreadLocal EF context

I have been having some strange errors with Entity Framework calls, and I am exploring the possibility they are due to concurrent multi-threaded access using the same ObjectContext . 我在使用Entity Framework调用时遇到了一些奇怪的错误,并且我正在探索它们是否可能是由于使用同一ObjectContext进行并发多线程访问所致。

I have tried to create a new context for every thread by putting the creation context inside ThreadLocal. 我试图通过将创建上下文放在ThreadLocal内为每个线程创建一个新上下文。

private System.Threading.ThreadLocal<EF.XYZEntities> threadLocalContext = new System.Threading.ThreadLocal<EF.XYZEntities>(() => new EF.XYZEntities(connectionString));
private EF.XYZEntities context { get { return threadLocalContext.Value; } }

This is not working. 这是行不通的。 The first use of that context throws an error: 该上下文的首次使用会引发错误:

Invalid object name 'dbo.Site'. 无效的对象名称“ dbo.Site”。

How can I get this to work? 我该如何工作?

Using a shared context is generally considered 'bad', unless you micro manage everything very well. 除非您很好地管理所有事情,否则通常认为使用共享上下文是“坏的”。 Using shared contexts that are not managed well can produce very strange results. 使用管理不善的共享上下文会产生非常奇怪的结果。

It's generally best practice to take a Unit of Work approach with the context as follows: 通常,最佳实践是在上下文中采用“工作单元”方法:

using (DBEntities ctx = new DBEntities())
{
    // Explicitly open the context connection yourself - to help prevent connection pooling / sharing
    // The connection will automatically be closed once exiting the using statement,  
    // but it won't hurt to put a ctx.Connection.Close(); after everything inside the using statement.
    ctx.Connection.Open();

    // Do Stuff

    // If necessary ctx.SaveChanges();
    // Not necessary but you could put a ctx.Connection.Close() here, for readability if nothing else.
}

UPDATE: In reply to Noseratio's comment below about async and EF. 更新:回应下面Noseratio关于异步和EF的评论。 Taken from here 从这里取

Non-Goals 非目标

The following are things we are explicitly not trying to enable with the feature in EF6: 以下是我们明确不尝试使用EF6中的功能启用的功能:

  • Thread safety 线程安全
  • Async lazy loading 异步延迟加载

Thread Safety 线程安全

While thread safety would make async more useful it is an orthogonal feature. 尽管线程安全性将使异步更加有用,但这是一个正交功能。 It is unclear that we could ever implement support for it in the most general case, given that EF interacts with a graph composed of user code to maintain state and there aren't easy ways to ensure that this code is also thread safe. 鉴于EF与由用户代码组成的图进行交互以维护状态,并且没有简单的方法来确保该代码也是线程安全的,因此我们尚无法在最一般的情况下实现对它的支持。

For the moment, EF will detect if the developer attempts to execute two async operations at one time and throw.... 目前,EF将检测开发人员是否试图一次执行两个异步操作并抛出...。

Async support in EF requires .NET 4.5 and will not be available on .NET 4. EF中的异步支持需要.NET 4.5,而在.NET 4上将不可用。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM