的TransactionScope和连接池连接池、TransactionScope

2023-09-07 04:25:12 作者:演绎的花瓣雨。

我试图让我们是否有一个问题,我们使用不正确IsolationLevels数据库连接的应用程序的句柄。我们的应用程序是使用SQL Server 2005中的.Net 3.5数据库的应用程序

I'm trying to get a handle on whether we have a problem in our application with database connections using incorrect IsolationLevels. Our application is a .Net 3.5 database app using SQL Server 2005.

我发现连接的IsolationLevel当他们返回到连接池(见的这里),也是真的很惊讶阅读此博客文章创建每个新的TransactionScope都有自己的连接池分配给它。

I've discovered that the IsolationLevel of connections are not reset when they are returned to the connection pool (see here) and was also really surprised to read in this blog post that each new TransactionScope created gets its own connection pool assigned to it.

我们的数据库更新(通过我们的业务对象)取一个TransactionScope(一个新的针对每个业务对象图更新创建)内进行。但是,我们取不使用显式事务。因此,我想知道是我们所能进入的地方我们的读取操作(这应该使用默认的IsolationLevel - 读已提交)的情况会重复使用已被用于更新池中的连接,并且继承了更新的IsolationLevel (REPEATABLEREAD)?或者将我们的更新来保证使用不同的连接池看到,因为它们被包裹在一个TransactionScope?

Our database updates (via our business objects) take place within a TransactionScope (a new one is created for each business object graph update). But our fetches do not use an explicit transaction. So what I'm wondering is could we ever get into the situation where our fetch operations (which should be using the default IsolationLevel - Read Committed) would reuse a connection from the pool which has been used for an update, and inherit the update IsolationLevel (RepeatableRead)? Or would our updates be guaranteed to use a different connection pool seeing as they are wrapped in a TransactionScope?

在此先感谢,

格雷厄姆

推荐答案

这是令人担忧的!

您挂指出,......每一个TransactionScope的都有自己的游泳池比尔·沃恩的文章,但code在您连接到支持文章,就认为是不正确的,因为 NoTxScope()会从它使用的高架隔离级别池的连接。

Bill Vaughan's article you linked to states that '...each TransactionScope gets its own pool', but the code in the support article you linked to, would suggest that is not true, since second run of NoTxScope() gets the connection from the pool which used the elevated Isolation level.

您可以力的问题,通过[我是从第一个环节借鉴了code]:

You can 'force' the issue by [I'm drawing on the code from the first link]:

static void ForceReadCommitedScope()
{
    TransactionOptions op = new TransactionOptions();
    op.IsolationLevel = IsolationLevel.ReadCommitted;
    using (TransactionScope tx = new TransactionScope(TransactionScopeOption.RequiresNew, op))
    {
        SqlConnection con = new SqlConnection("Data Source=.;Initial Catalog=master;Integrated Security=True;");
        SqlCommand com = new SqlCommand("select transaction_isolation_level from sys.dm_exec_sessions where (session_id = @@SPID)", con);
        con.Open();
        short level = (short)com.ExecuteScalar();
        Console.WriteLine("transaction_isolation_level : " + level.ToString());
        con.Close();
        tx.Complete();
    }
}

或通过添加..;池=假。来连接字符串