MS SQL Server的Hibernate隔离问题。阅读锁

发布于 2025-02-14 01:35:41 字数 1774 浏览 0 评论 0原文

我的业务逻辑非常重。我将Spring Data JPA与Microsoft SQL Server一起使用。我的代码看起来像这样。

@Transactional(rollbackFor = Exception.class)
public void executeAllFlows() {

    RandomTableObject a = randomTableObjectRepository.findById(1L);
    executeFlow1();
    executeFlow2();
    executeFlow3();
    executeFlow4();
    
    a.setSomeAttribute(true);
    randomTableObjectRepository.save(a);

}

@Transactional(rollbackFor = Exception.class)
private void executeFlow1() {
//read items from tempTable 1 and persist them in other 2 tables after performing logic
}

@Transactional(rollbackFor = Exception.class)
private void executeFlow2() {
//read items from tempTable 2 and persist them in other 2 tables after performing logic
}

@Transactional(rollbackFor = Exception.class)
private void executeFlow3() {
//read items from tempTable 3 and persist them in other 2 tables after performing logic
}

@Transactional(rollbackFor = Exception.class)
private void executeFlow4() {
//read items from tempTable 4 and persist them in other 2 tables after performing logic
}

由于涉及成千上万的记录,因此此过程可能需要长达两分钟。 如果某事失败,所有表都会回滚。这就是我想要的。

当我想在此过程运行时进行一些肮脏的读数时,就会发生问题。 当过程开始运行时,我尝试从RandomTableObject的表中读取。 在过程开始时,我得到结果,但是几秒钟后,它延迟了结果,直到整个过程结束。

似乎当Hibernate从该表中选择并开始修改记录时,实现了读取锁。 Hibernate的默认行为不是要执行读取锁,因此我的下一个可疑是MS SQL Server的隔离级别。

根据MS SQL Server的此文档: 隔离级别读取不合格允许肮脏的读数。我试图通过在每种方法上方添加上述来实施此功能,

@Transactional(rollbackFor = Exception.class , isolation = Isolation.READ_UNCOMMITTED)

但这并不能解决问题。导入来自org.springframework.transactions.annotation。

是否有人对我有同样的问题,如果是的,是否有任何解决方案。

i have a really heavy business logic. I use spring data jpa with microsoft sql server. My code looks like this.

@Transactional(rollbackFor = Exception.class)
public void executeAllFlows() {

    RandomTableObject a = randomTableObjectRepository.findById(1L);
    executeFlow1();
    executeFlow2();
    executeFlow3();
    executeFlow4();
    
    a.setSomeAttribute(true);
    randomTableObjectRepository.save(a);

}

@Transactional(rollbackFor = Exception.class)
private void executeFlow1() {
//read items from tempTable 1 and persist them in other 2 tables after performing logic
}

@Transactional(rollbackFor = Exception.class)
private void executeFlow2() {
//read items from tempTable 2 and persist them in other 2 tables after performing logic
}

@Transactional(rollbackFor = Exception.class)
private void executeFlow3() {
//read items from tempTable 3 and persist them in other 2 tables after performing logic
}

@Transactional(rollbackFor = Exception.class)
private void executeFlow4() {
//read items from tempTable 4 and persist them in other 2 tables after performing logic
}

This process may take up to two minutes because there are thousands of records involved.
If something fails all tables go on rollback. Which is what i want.

The problem occurs when i want to do some dirty reads while this process runs.
While the process starts running i try to read from the table of RandomTableObject.
At the start of the process i get result but after a few seconds it delays the result until the whole process ends.

It seems while hibernate selects from this table and starts modifying the record a read lock is implemented. Default behavior of hibernate is not to enforce read locks so my next suspect are isolation levels of ms sql server.

According to this documentation of ms sql server:
Understanding isolation levels
Isolation level Read uncommitted allows dirty reads. I tried to enforce this by adding

@Transactional(rollbackFor = Exception.class , isolation = Isolation.READ_UNCOMMITTED)

above each method but this does not solve the problem. The import is from org.springframework.transactions.annotation.

Has anyone had the same problem with me and if yes is there any solution to this.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。
列表为空,暂无数据
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文