sql-server - Microsoft DTC 无法很好地处理存储过程中的事务

标签 sql-server msdtc

我遇到了 DTC 不配合的问题。我有两台服务器,我们将其称为服务器 A 和服务器 B(不同版本、不同物理机、相同域和相同网络)。

我在服务器 A 上有两个存储过程,它们执行相同的操作,即从 API(相同的 API)获取数据并最终将其插入到服务器 B 上的表中。一个存储过程将所有功能包装在 try/中catch block ,一切正常。第二个存储过程执行相同的操作,添加所有包含在事务中的“尝试”内容(以便在出现问题时我可以回滚)。这会导致错误 - 如下所示。

OLE DB provider "SQLNCLI11" for linked server "[Server B]" returned message "The partner transaction manager has disabled its support for remote/network transactions.".
Msg 7391, Level 16, State 2, Line 105
The operation could not be performed because OLE DB provider "SQLNCLI11" for linked server "[Server B]" was unable to begin a distributed transaction.

我在没有交易的情况下测试了它,它似乎工作得很好,尽管我更喜欢在那里有交易。经过一番研究,我发现了一个设置,在了解其效果之前我有点犹豫是否要使用它。

link to the article: https://learn.microsoft.com/en-us/sql/relational-databases/system-stored-procedures/sp-serveroption-transact-sql?view=sql-server-2017
setting in question: remote proc transaction promotion

我将其设置为以下代码段,在运行跨服务器插入之前我会将其翻转到“关闭”位置,并在我完成后将其重新打开(这是默认设置)完毕。

EXEC sp_serveroption 
     @server = '[Server B]'
    ,@optname = 'remote proc transaction promotion'
    ,@optvalue = 'false';

这是解决问题的正确方法吗?

最佳答案

链接服务器存在的一个关键原因是使 DBA/管理员能够明确限制给定 SQL Server 和它可能与之交互的任何其他框/服务之间可能存在的连接和事件类型(假设某些SQL Server 附带的库和内置功能可帮助“跨”平台和跨主机通信)。

有关这方面的更多背景信息,请注意禁用临时分布式查询的意图: https://learn.microsoft.com/en-us/sql/database-engine/configure-windows/ad-hoc-distributed-queries-server-configuration-option?view=sql-server-2017

默认情况下,不允许进行临时分布式查询(防止某人有效地运行“SELECT * INTO OPENDATASOURCE('我车库里一个盒子上的远程表',开关,此处)”FROM dbo.SuperSensitiveInfo “并将敏感数据‘流式传输’到 AD HOC 端点)。

或者,换句话说,链接服务器不仅仅是为了使连接更简单/更容易(通过将它们定义为通用映射端点,这样可以更轻松地查询 OPEN*() 操作),而是让 DBA/管理员可以“发出信号”,表明这些端点具有足够的信任度,以便管理员明确创建连接。

所有这些都是说:链接服务器存在的一个关键原因是帮助“定义”给定 SQL Server 可能与之通信的安全端点 - 以及确切的条件(即允许什么和不允许什么) )。因此,从这个意义上说,链接服务器有点像给 child 一部智能手机,他们只能使用电话应用程序,并且不允许他们调用任何号码 - 但只能调用您的联系人我们已定义 - 以便他们可以与 friend 交谈并给您打电话,但不能调用任何“临时”电话。

以这种“心态”为背景,远程过程事务提升代表了一种可以针对链接服务器启用(好吧,禁用或未禁用)的提升的“权限”IF那里有足够的信任。

或者,换句话说,如果您信任 ServerA 和 ServerB 之间的关系,并且您同意他们一起玩 DTC-footsie,那么我会设置(并“忘记”)此链接服务器设置,而不是在/之前切换它启用此特定存储过程后。

否则,我相信您可以/可以通过在操作系统/服务器级别本身启用网络 DTC,按照如下步骤简单地绕过 SQL Server 此处的附加限制(针对默认的 DTC 登记): https://support.resolver.com/hc/en-ca/articles/207161116-Configure-Microsoft-Distributed-Transaction-Coordinator-MSDTC-

关于sql-server - Microsoft DTC 无法很好地处理存储过程中的事务,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/55166369/

相关文章:

.net - 用于 Windows Server 事务/错误处理的服务总线 1.0

sql-server - 由于通信问题,MSDTC 事务管理器无法将事务推送到目标事务管理器

transactions - 嵌套 ADO.NET 事务损坏的连接池(使用 MSDTC)

asp.net - 如何在 EF DbContext 和 AspNet Membership 之间共享连接以避免事务升级到 DTC

c# - SQL Server 的 NHibernate 超时

C# Entity Framework 4 导航属性导致提交时性能下降

c# - 如何根据 Microsoft.SqlServer.Management.Smo.Transfer 中的架构名称复制表

混合了 LEFT 连接和 INNER 连接的 SQL 查询

sql-server - 存储过程中的 SQL case 语句

sql - Always On 可用性组中的 MSDTC