- c - 在位数组中找到第一个零
- linux - Unix 显示有关匹配两种模式之一的文件的信息
- 正则表达式替换多个文件
- linux - 隐藏来自 xtrace 的命令
我们的许多 DAL 代码都使用 TransactionScope 进行交易。这很好用,但是当我从 SQLCLR 过程内部使用此 DAL 代码时出现问题。事务升级到 MSDTC,这是我不想要的。
问题很容易重现:
CLR 实现
[SqlProcedure]
public static void ClrWithScope(string cmdText)
{
/* escalates to MSDTC when a transaction is already open */
using ( var scope = new TransactionScope())
{
using (var connection = new SqlConnection("context connection=true;"))
{
connection.Open();
using (var cmd = new SqlCommand(cmdText, connection))
{
SqlContext.Pipe.ExecuteAndSend(cmd);
}
}
scope.Complete();
}
}
[SqlProcedure]
public static void ClrWithTrans(string cmdText)
{
/* works as expected (without MSDTC escalation ) */
using (var connection = new SqlConnection("context connection=true;"))
{
connection.Open();
using (var tx = connection.BeginTransaction())
{
using (var cmd = new SqlCommand(cmdText, connection, tx))
{
SqlContext.Pipe.ExecuteAndSend(cmd);
tx.Commit();
}
}
}
}
用于执行 CLR 过程的 SQL 脚本
BEGIN TRANSACTION
exec dbo.ClrWithTrans "select * from sys.tables";
exec dbo.ClrWithScope "select * from sys.tables"; /* <- DOES NOT WORK! */
ROLLBACK TRANSACTION
错误
Msg 6549, Level 16, State 1, Procedure ClrWithScope, Line 0
A .NET Framework error occurred during execution of user defined routine or aggregate 'clrClrWithScope':
System.Transactions.TransactionAbortedException: Die Transaktion wurde abgebrochen. ---> System.Transactions.TransactionPromotionException: MSDTC on server 'BLABLA' is unavailable. ---> System.Data.SqlClient.SqlException: MSDTC on server 'BLABLA' is unavailable.
System.Data.SqlClient.SqlException:
bei System.Data.SqlServer.Internal.StandardEventSink.HandleErrors()
bei System.Data.SqlServer.Internal.ClrLevelContext.SuperiorTransaction.Promote()
System.Transactions.TransactionPromotionException:
bei System.Data.SqlServer.Internal.ClrLevelContext.SuperiorTransaction.Promote()
bei System.Transactions.TransactionStatePSPEOperation.PSPEPromote(InternalTransaction tx)
bei System.Transactions.TransactionStateDelegatedBase.EnterState(InternalTransaction tx)
System.Transactions.TransactionAbortedException:
bei System.Transactions.TransactionStateAborted.CreateAbortingClone(InternalTransaction tx)
bei System.Transactions.DependentTransaction..ctor(IsolationLevel isoLevel, InternalTransaction internalTransaction, Boolean blocking)
bei System.Transactions.Transaction.DependentClone(DependentCloneOption cloneOption)
bei System.Transactions.TransactionScope.SetCurrent(Transaction newCurrent)
bei System.Transactions.TransactionScope.PushScope()
bei System.Transactions.TransactionScope..ctor(TransactionScopeOption scopeOption)
bei Giag.Silo.Data.SqlClr.ClrWithScope(String cmdText)
. User transaction, if any, will be rolled back.
没有“BEGIN TRANSACTION”语句,dbo.ClrWithScope 调用工作正常。我想在 .Net Framework 中登记时不考虑由 SQLServer 启动的事务。
有没有办法解决这个问题。一个想法是手动创建一个 SqlTransaction 并使 TransactionScope 使用此事务,但我不知道该怎么做。另一种解决方案是在所有 DAL 代码中创建一个特例(实现起来并不有趣)。
有什么想法吗?
最佳答案
在 SQL CLR 中使用 TransactionScope 将始终提升/升级为 MSDTC 事务。似乎没有任何办法解决这个问题,即使在 SQL 2012 中也是如此。
来自 TechNet 关于 SQL CLR 和 TransactionScope ( http://technet.microsoft.com/en-us/library/ms131084.aspx )
TransactionScope should be used only when local and remote data sources or external resource managers are being accessed. This is because TransactionScope always causes transactions to promote, even if it is being used only within a context connection.
关于c# - 如何在不升级到 MSDTC 的情况下在 SQLCLR 中使用 TransactionScope,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12138091/
我有一个应用程序,我想将多个数据库保存到一个事务中。如果他们中的任何一个失败了,我想把整个事情都推回去。但是,我想在回滚事务之前知道其中哪些失败(或成功)。 我有一个带有内部循环的外部 Transac
我刚刚开始玩 Dapper。到目前为止我很喜欢它。 dapper 不能与 TransactionScope 一起使用吗?我注意到,即使我从不调用 TransactionScope.Complete,我
您好首先感谢您对这个问题的关注;有没有办法在c#中实现这样的事务 using (Transactionscope x=new Transactionscope ()) { Thead A()=>
这是使用事务范围的正确方法吗: 我有一个代表事物的一部分的对象: public class ThingPart { private DbProviderFactory connectionFa
我正在尝试找到在使用 NHibernate 的 Web 应用程序中处理事务的最佳解决方案。 我们使用 IHttpModule 并在 HttpApplication.BeginRequest 我们打开一
我面临以下问题: 在我的项目中,我在应用程序正在使用的同一个数据库中进行了错误登录。这意味着,如果发生错误,那么在每个 catch 中,都会将错误存储到 DB 中。 然而,问题是在使用事务时。发生错误
我想知道在处理多线程时如何正确使用 TransactionScope 类? 我们在主线程中创建一个新的作用域,然后生成几个工作线程,我们希望它们参与主作用域,因此,如果作用域从未完成,则在每个工作线程
任何人都可以给我一个关于使用 TransactionScope 和 NHibernate 的快速概述吗?我需要对 session /IEnlistmentNotification/等做一些特别的事情吗
如果我执行以下操作: Using scope = New TransactionScope() entries.Content.ReadAs(Of IList(Of WebMaint
当 TransactionScope 首次推出时,我在让它在我的开发机器 (XP) 和我们的数据库服务器 (Windows Server 2003) 之间工作时遇到了一些严重的问题。 当我进一步研究时
我在基于 Silverlight 和 RIA 服务的项目中使用 TransactionScope 类。每次我需要保存一些数据时,我都会创建一个 TransactionScope 对象,使用 Oracl
TransactionScope 是否适用于封闭的数据库连接? using (var transaction = new TransactionScope(TransactionScopeOption
我有两个 PL/SQL 存储过程,每个过程都处理自己的事务(开始/提交和发生错误时的回滚)。从 .Net 代码我调用这两个 SP,如下所示。 using (TransactionScope ts
我在我的应用程序中使用了 TransactionScope 类,因为我需要以交互方式、自然地执行一些操作(要么全部成功,要么全都不成功)。 由于此操作不仅与数据库相关,我通过实现 IEnlistmen
您好,有没有办法检查使用 TransactionScope 的事务是提交还是回滚? 最佳答案 在处理 TransactionScope 之前,实际的提交不会发生。如果 Commit 由于任何原因失败,
我有一个 Web 应用程序,许多用户在任何给定时刻都在使用它。从数据库的角度来看,他们在系统中移动时不断地从任意数量的表中写入和读取数据。此外,我们还有许多将数据导入该系统的流程。 今天,在调试导入过
我正在开发一个使用 C# 和 SQL Server 作为数据库的 .NET Web 应用程序,我是这两种技术的新手。当我尝试同时保存大量信息时遇到问题。 我的代码很简单: SqlConnectio
您好,我在我的应用程序的多个位置使用了 TransactionScope。喜欢: using (var scope = new TransactionScope()) { ToDo1(
我在服务器端代码 (WCF) 中使用 TransactionScope 类时遇到性能问题。 我的代码从客户端获取请求,创建 TransactionScope 并执行短操作(通常最多 100 毫秒)。
我正在处理一个几乎不存在事务的遗留项目,这会在出现错误时导致大量的部分提交。 SQL 调用混合了原始 ADO、Linq to Entities 和 EntityFramework,我想让它们在事务中运
我是一名优秀的程序员,十分优秀!