c# - 为什么失败的事务不使用 TransactionScope 回滚?
问题描述
我想要实现的是:我从 2 个不同的数据库调用存储过程。SP 在表中有一个简单的插入条目。如果两个事务都成功,则没有问题,但是当我尝试在第二个 DB SP 中引发异常时,第一个不会回滚。我在这里做错了什么?
C#代码:
using (TransactionScope scope = new TransactionScope(TransactionScopeOption.Suppress))
{
// Update DB1
using (SqlConnection con = new SqlConnection(connectionString1))
{
con.Open();
SqlCommand command1 = new SqlCommand("sp_1", con);
command1.ExecuteNonQuery();
// Update DB2
using (SqlConnection con2 = new SqlConnection(connectionString2))
{
con2.Open();
SqlCommand command2 = new SqlCommand("sp_2", con2);
command2.ExecuteNonQuery();
}
}
scope.Complete();
}
DB1 SP:
BEGIN
INSERT INTO TABLE_X1 VALUES(...)
END
DB2 SP:
BEGIN
THROW 51000, 'The record does not exist.', 1;
INSERT INTO TABLE_X2 VALUES(...)
END
解决方案
您需要使用TransactionScopeOption.Required
选项来启用交易。
如果两个数据库在同一个 SQL 服务器上,则使用相同的连接以避免触发分布式事务(如果连接字符串完全相同,则不应发生这种情况)。
如果您要使用事务并且如果数据库位于不同的服务器上(或同一服务器上的不同实例),那么就无法避免分布式事务。在这种情况下,启用 MSDTC,请参阅此处的详细信息
推荐阅读
- php - 使用 PHP 和 SQL 删除表条目
- python - 从夹具返回结构化数据的正确方法是什么?
- powershell - 将更改的 CSV 数据复制到新的 CSV
- sql - SQL 视图错误 - 消息 207,级别 16,状态 1,过程 OrderItems_vw,第 16 行 [批处理开始行 0] 无效的列名“品牌”
- graphql - GraphQL 客户端未读取某些查询变量
- python - 如何在 Django 中将消息线程渲染为模板?
- c# - 迁移到 ASP CORE 3:如何迁移后台服务?(通过 AddHostedService 添加的服务会冻结 Web 应用程序启动)
- spring-boot - 是否可以在具有 RequestBody 和 RequestPart 的控制器中定义端点?
- javascript - 动态更改 Dropzone maxFiles
- regex - 大骆驼大写到小骆驼大写作为 VS 代码片段