【发布时间】:2021-06-15 04:25:43
【问题描述】:
在 Web 服务中,我正在查询 SQL Server 2016 数据库。使用 .NET TransactionScope 如下在我的服务层中保留事务管理,但在我的数据层(“存储”类)代码中保留数据查询/命令,我们有几个地方遵循这种模式:
using (var transaction = new TransactionScope(TransactionScopeAsyncFlowOption.Enabled))
{
bool needsInsert = await store1.Exists(request.id);
if (needsInsert) mainRowsUpdatedCount = await store2.Insert(request);
transaction.Complete();
}
这些“存储”方法中的每一个都遵循这种模式(使用 Dapper,虽然我怀疑这并不重要):
const string query = @"SELECT ..."; // or INSERT or MERGE as the case may be
using IDbConnection connection = new SqlConnection(ConnectionString.Value);
return await connection.QueryAsync<T>(query, new { ... }); // or connection.ExecuteAsync as the case may be
这在大多数调用中都非常有效,但有时我会收到以下信息(尽管很少见):
System.PlatformNotSupportedException:此平台不支持分布式事务。
那么,在上面的例子中,store1.Exists 运行,获取连接,在事务中登记它,运行它的查询,关闭,然后有时在 store2.Insert 可以运行之前,其他一些不相关的线程从已打开事务的连接池获取相同的连接,尝试运行查询并因此引发 PlatformNotSupportedException,因为 .NET Core(或 .NET 5+)不支持分布式事务?
如果是这样,我怎样才能在不传递我的连接的情况下克服这个问题?
如果不是,还有什么可能导致此异常?
【问题讨论】:
-
尝试升级到分布式事务,也许?如果没有“支持”这种“支持”的 MSDTC,我会期待同样的结果。
-
“升级为分布式事务”是什么意思?
-
我想知道是否有一些 TS代码没有使用
TransactionScopeAsyncFlowOption.Enabled?如果虔诚地使用RequiresNew,错误可能会“消失”,这将避免加入现有事务。 -
RequiresNew 可能正是我所需要的。谢谢,我试试看。
-
这方面有进展吗?我们遇到同样的问题,也很少,但仍然存在。 “RequiresNew”不是一个选项,因为我们想加入任何正在进行的外部交易,如果有的话。但是“RequiresNew”是否解决了您的问题?
标签: c# .net-core sqlconnection transactionscope system.data.sqlclient