nHibernate锁定-在同一行上读取NONE后进行LockMode UPGRADE阻塞

本文关键字:NONE 读取 阻塞 UPGRADE LockMode 锁定 nHibernate 一行 | 更新日期: 2023-09-27 18:05:27

我们有一个卡片订单流程,可能需要几秒钟才能运行。该进程中的数据以LockMode方式运行。

第二个(webhook)进程以LockMode运行。NONE偶尔会在第一个订单流程完成创建竞争条件之前被触发,并且看起来正在使用原始行数据。它不会被阻塞,直到第一个完成,所以旧的数据。

由于我们的数据库没有以NO WAIT或任何其他SNAPSHOT COMMITTED设置运行。

我的问题是:可以锁定模式。none忽略升级锁,读取旧数据(可能是缓存?)

谢谢。

nHibernate锁定-在同一行上读取NONE后进行LockMode UPGRADE阻塞

升级锁是为了防止另一个事务也获取相同的数据进行升级。

在没有额外锁的情况下以读提交模式运行的事务仍然可以读取它们。您需要一个排他锁来阻塞已提交的读(前提是它们没有快照隔离级别)。在Technet上阅读更多内容。

据我所知,NHibernate没有提供在实体读时发出排他锁的方法。(您将通过实际更新事务中的实体来获得它们。)您可以通过使用CreateSQLQuery直接在DB中发出锁来解决这个问题。或者在你的webhook进程中,也获取升级锁。

但是这个路径肯定会导致死锁或锁争用。

一般来说,通过调整代码模式来避免显式锁定是可取的。我刚刚在这里写了一个例子,看看"无显式锁"的解决方案。

关于你的webhook进程,这两种情况真的有区别吗?

  1. 它获取它的数据,它没有任何更新锁,但在处理它之前,它的数据被订单进程更新。
  2. 它获取它的数据,包括一些有更新锁的数据。

一般情况下,你仍然会有同样的麻烦要解决,并避免2。将不解决1。在这里,这也是流程处理其数据的方式,需要对其进行调整以支持并发性。(提示:使用长时间运行的事务来解决1。