当前位置: 首页 > 知识库问答 >
问题:

Spring@Transactional和Hibernate@LockMode注释如何相关

凌翔宇
2023-03-14

我想知道交易和锁之间的关系。

更具体地说,Spring的< code>@Transactional与Hibernate的LockMode有什么关系。https://docs . JBoss . org/hibernate/ORM/4.0/dev guide/en-US/html/ch05 . html . http://docs . spring . io/auto repo/docs/spring/4.2 . x/spring-framework-reference/html/transaction . html

如果我在创建会话对象时没有指定任何锁,并将@TransactionalreadOnly作为 一起使用,那么我是否在使用悲观并发控制。

如果有人能告诉我(乐观/悲观)并发控制和事务之间的关系,这将是一个很大的帮助。

谢谢你,维维克

共有2个答案

颛孙轩昂
2023-03-14

Spring的@Transactional和Hibernate的LockMode类是不同的。

Spring事务管理

@Transactional 是用于声明式事务管理的 Spring 注释,即定义在数据库事务中一起执行哪些 SQL 语句。例如,使用 readOnly 属性允许 Spring 在尝试在只读事务中插入行时抛出异常。

但是,关于锁定,您很可能会使用读/写(readOnly = false)事务,因为您将尝试修改数据。

悲观锁定

Hibernate的< code>LockMode用于悲观锁定,例如< code>LockMode。升级实际上执行一个< code >选择...FOR UPDATE语句,并锁定数据库中与该实体对应的行。

悲观锁定假定并发事务将相互冲突,并要求资源在读取后锁定,并且仅在应用程序使用完数据后解锁。

乐观锁定

Hibernate中的乐观并发控制通常使用数据库中的版本或时间戳列。这里的想法是,如果多个事务试图同时修改一行,那么除了第一个提交的事务之外,所有事务都将检测到版本号已更改并执行回滚。

乐观锁定假定多个事务可以在不相互影响的情况下完成,因此事务可以在不锁定它们影响的数据资源的情况下继续进行。在提交之前,每个事务都验证没有其他事务修改了它的数据。如果检查显示有冲突的修改,则提交事务回滚。

以上引文来自:https://docs . JBoss . org/hibernate/ORM/4.0/dev guide/en-US/html/ch05 . html

张智
2023-03-14

@Transactionic@Lock模式注解之间没有直接关系。

@Transactional用于标记RESOURCE_LOCAL或JTA事务的显式边界。之所以需要它,是因为每个数据库语句都在事务上下文中执行,如果不设置事务边界,则每个语句或自动提交都会有一个事务。

另一方面,@LockModeType用于设置显式锁定选项。如果不设置,将使用隐式锁定机制:

  • 在2PL和MVCC数据库引擎上的每个修改行上都会获取隐式锁。如果在可串行化上使用可重复读取,则会在2PL引擎上的读取记录上获取共享锁
  • 如果您定义@Version属性,则将使用隐式乐观锁定机制

因此,@LockModeType用于显式设置锁定选项,您可以有以下选项:

  • LockModeType.PESSIMISTIC_READ
  • LockModeType.PESSIMISTIC_WRITE

< code >悲观锁模式将始终获取与锁定实体相关联的表行上的数据库锁。

还有显式的乐观锁策略:

    < li> LockModeType。乐观 < li> LockModeType。OPTIMISTIC _ FORCE _ INCREMENT < li> LockModeType。悲观_强制_增量

乐观锁定模式旨在为您提供一种提升实体版本的方法,即使实体在当前运行的持久性上下文中没有更改。当您需要使用父实体版本的多个子实体进行协调时,这是一种非常有用的机制。

我在这个答案中提供的链接中有很多示例,所以请花点时间,通读它们,你会更详细地理解所有这些概念。

 类似资料:
  • 问题内容: 我必须在Web应用程序中使用3个不同的事务管理器。因此,我根据Spring参考(第10.5.6.3节“自定义快捷方式注释”)编写了自己的注释。 一个注释(用于使用一个特定的transactionmanager)如下所示: 使用自定义的@CustomerTX批注对我的服务层进行批注时,一切工作正常。但是我必须为注释提供更多选项,例如readonly = true,rollbackFor

  • 问题内容: 我已成功将此注释用于Dao类。回滚适用于测试。 但是现在我需要回滚真实代码,而不仅仅是测试。有用于测试的特殊注释。但是哪些注释适用于非测试代码?对我来说这是一个大问题。我已经花了一天的时间。官方文档不符合我的需求。 employeeDao is 这是一个注释可以很好地运行的测试: HibernateDaoBeans.xml 是的,我回滚了交易。我刚刚为服务添加了BEAN …,然后注释@

  • 问题内容: 我的@Transactionnal注释似乎被忽略了。我对Spring容器的初始化没有任何错误。看来我的方法尚未被Spring TX框架代理。在执行服务的方法期间,JDBCTemplate会引发预期的RuntimeException。问题在于JDBC连接没有回滚,并且更改保持不变。stacktrace没有显示应该包装我的服务方法的代理的任何迹象。 编辑:添加了控制器的代码 编辑2:添加了

  • 我不明白的是为什么人们说自我调用会破坏交易?只要调用方方法是事务性的,难道一切都不应该像预期的那样工作吗?我有什么遗漏吗?

  • 我正在使用带有webflux的spring boot 2.4.2连接到postgres数据库。我在使用事务性代码时观察到了一个我不理解的行为。 为了展示这种行为,我创建了一个示例应用程序,试图将行添加到两个表中;表“a”和表“b”。对表“a”的插入预计将失败,并出现重复密钥冲突。考虑到使用了事务性,我希望不会向表“b”中添加任何行。 然而,根据我用哪个方法注释事务,我会得到不同的结果。 如果我对c

  • 我有一个与交易中的交易有关的疑问。作为背景,我有一个School实体对象,它有一组映射到它的Students实体对象。我使用的是Spring Data JPA,它负责所有的crud操作。我有一个SchoolManagementService类,它在类级别设置了@transactional(readonly=true),对于所有更新方法,我都在它们上面使用@transactional。在我的Scho