从 JPA PESSIMISTIC 锁获取的数据库行的物理锁
Physical lock on DB rows obtained from a JPA PESSIMISTIC lock
根据 JPA 2.1 规范...
The lock modes PESSIMISTIC_READ
, PESSIMISTIC_WRITE
, and
PESSIMISTIC_FORCE_INCREMENT
are used to immediately obtain long-term
database locks.
我假设悲观锁总是会在数据库上触发 SELECT ... FOR UPDATE
SQL,无论使用何种锁定模式。现在三个问题:
- 这个假设是否正确,或者如果正确的话,这条规则有例外吗?
- 给定
SELECT ... FOR UPDATE
锁定行。除了锁定它的事务之外,任何其他事务都不能更新锁定的行?
- 可以通过对事务执行提交或回滚来释放锁。如果应用程序(以及锁定行的事务)在没有对事务进行提交或回滚的情况下突然终止,锁会发生什么情况?
对于问题1和2,你的假设是正确的:
是——悲观锁一般使用SELECT ... FOR UPDATE
,因为大多数数据库和JPA实现只支持这种类型的锁。在这种情况下,READ 和 WRITE 块之间没有区别,只要两者都表现为 WRITE 锁,JPA 规范就允许它。
是 - 锁定的行不能被任何其他事务修改。在 WRITE 锁的情况下(大多数情况下也用于 READ 锁 - se answer for 1),在释放锁之前也无法读取锁定的行。请注意,同一 table 中的其他未锁定行可以自由读取和修改。
同时回答问题 3:
- 是 - 在提交或回滚时释放锁。但是,当发生错误、连接断开或事务时间过长时,回滚也会自动发生。因此,当应用程序死亡时,会立即触发回滚。如果没有,它会在超时(通常是 5 分钟)后回滚。
根据 JPA 2.1 规范...
The lock modes
PESSIMISTIC_READ
,PESSIMISTIC_WRITE
, andPESSIMISTIC_FORCE_INCREMENT
are used to immediately obtain long-term database locks.
我假设悲观锁总是会在数据库上触发 SELECT ... FOR UPDATE
SQL,无论使用何种锁定模式。现在三个问题:
- 这个假设是否正确,或者如果正确的话,这条规则有例外吗?
- 给定
SELECT ... FOR UPDATE
锁定行。除了锁定它的事务之外,任何其他事务都不能更新锁定的行? - 可以通过对事务执行提交或回滚来释放锁。如果应用程序(以及锁定行的事务)在没有对事务进行提交或回滚的情况下突然终止,锁会发生什么情况?
对于问题1和2,你的假设是正确的:
是——悲观锁一般使用
SELECT ... FOR UPDATE
,因为大多数数据库和JPA实现只支持这种类型的锁。在这种情况下,READ 和 WRITE 块之间没有区别,只要两者都表现为 WRITE 锁,JPA 规范就允许它。是 - 锁定的行不能被任何其他事务修改。在 WRITE 锁的情况下(大多数情况下也用于 READ 锁 - se answer for 1),在释放锁之前也无法读取锁定的行。请注意,同一 table 中的其他未锁定行可以自由读取和修改。
同时回答问题 3:
- 是 - 在提交或回滚时释放锁。但是,当发生错误、连接断开或事务时间过长时,回滚也会自动发生。因此,当应用程序死亡时,会立即触发回滚。如果没有,它会在超时(通常是 5 分钟)后回滚。