如何在asp.net应用程序中实现“悲观锁定”?

时间:2009-03-06 07:14:22

标签: asp.net locking

我希望任何有经验的人在asp.net应用程序中实现“悲观锁定”之类的建议。这是我正在寻找的行为:

  1. 用户A打开订单#313
  2. 用户B尝试打开#313订单,但被告知用户A已经在X分钟内打开了该订单。
  3. 由于我之前没有实现过这个功能,我有一些设计问题:

    • 我应该在订单记录中附加哪些数据?我在考虑:
      • LockOwnedBy
      • LockAcquiredTime
      • LockRefreshedTime

    如果LockRefreshedTime<我将考虑解锁记录。 (现在 - 10分钟)。

    • 我如何保证锁定时间不超过必要但不会意外到期?

    我对jQuery很满意,所以欢迎使用客户端脚本的方法。这将是一个内部Web应用程序,所以我可以相当自由地使用带宽/周期。我也想知道“悲观锁定”是否适合这个概念。

2 个答案:

答案 0 :(得分:8)

听起来你大部分都在那里。我不认为你真的需要LockRefreshedTime,它并没有真正添加任何东西。您也可以使用LockAcquiredTime来确定锁何时变得陈旧。

您要做的另一件事是确保您使用交易。您需要在数据库事务中包装锁的检查和设置,这样您就不会得到两个认为具有有效锁的用户。

如果您的任务需要在多个资源上获取锁定(即,给定类型的多个记录或多于一种类型的记录),则无论何时执行锁定,都需要以相同的顺序应用锁定。否则你可以有一个死锁,其中一位代码已经锁定记录A并且想要锁定记录B而另一位代码已经B锁定并且正在等待记录A.

关于如何确保未意外释放锁定。确保如果您有任何长时间运行的进程可以运行超过锁定超时,那么它会在运行期间刷新其锁定。

术语“显式锁定”也用于描述锁定时间。

答案 1 :(得分:1)

我已手动完成此操作。

  • 将记录的主键存储到锁定表中,并标记记录 要编辑的模式属性。
  • 当其他用户尝试选择此记录时,请指明用户 准备就绪记录。
  • 设置锁定记录的最长时间。
  • 刷新锁定记录的页面数据。允许用户使用 进行更改后,所有其他用户都只能查看。

锁定表的设计应与此类似:

User_ID, //who locked
Lock_start_Time,
Locked_Row_ID(Entity_ID), //this is primary key of the table of locked row.
Table_Name(Entity_Name) //table name of the locked row.

剩下的逻辑是你必须要弄清楚的。

这只是我在4年前根据客户的特殊要求实施的一个想法。在那个客户之后没有人再次要我做类似的事情,所以我还没有实现任何其他方法。