乐观锁批量更新
如何使用乐观锁进行批量更新?我正在使用 SimpleJdbcTemplate,对于单行,我可以构建更新 sql,它会增加版本列值并在 WHERE 子句中包含版本。
不幸的是,使用 Oracle 驱动程序时,结果 int[] Updated = simpleJdbcTemplate.batchUpdate
不包含行计数。所有元素均为 -2,表示行数未知。
除了单独执行所有更新之外,还有其他更高效的方法吗?这些批次平均包含 5 个项目(仅),但可能最多 250 个。
How to use optimistic locking with batch updates? I am using SimpleJdbcTemplate
and for a single row I can build update sql that increments version column value and includes version in WHERE clause.
Unfortunately the result int[] updated = simpleJdbcTemplate.batchUpdate
does not contain rowcounts when using oracle driver. All elements are -2 indicating unknown rowcount.
Is there some other, more performant way of doing this than executing all updates individually? These batches contain an average of 5 items (only) but may be up to 250.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
当我在 Hibernate 工作时,我们注意到旧的 Oracle JDBC 驱动程序版本没有正确报告更新计数,这就是 Hibernate 使用乐观锁定禁用实体批量更新的原因。
然而,从 Hibernate 5 开始,这不再是默认策略,因为 JDBC 驱动程序可以更好地处理批量更新计数。
因此,对于您的情况,您需要将 Oracle JDBC 驱动程序更新到至少 12c。请注意,Oracle JDBC 驱动程序向后和向前兼容,因此您甚至可以在数据库服务器端与 Oracle 11g 一起使用它。
自 2019 年 9 月起,您甚至可以从 Maven Central 获取 Oracle JDBC 驱动程序:
我将驱动程序版本 19 与 Oracle 18 XE 一起使用,即使将批量更新与乐观锁定混合使用,它也能发挥作用。
When I was working for Hibernate, we noticed that the older Oracle JDBC Driver versions did not report the update count correctly, and that's why Hibernate used to disable batch updates for entities using optimistic locking.
However, since Hibernate 5, this is no longer the default strategy as JDBC drivers handle the batch update count better.
So, in your case, you need to update the Oracle JDBC Driver to at least 12c. Note that the Oracle JDBC Driver is both backward and forward compatible, so you can use it even with Oracle 11g on the database server-side.
Since September 2019, you can even get the Oracle JDBC Driver from Maven Central:
I'm using version 19 of the driver with Oracle 18 XE, and it works like a charm even when mixing batch updates with optimistic locking.
只是在这里大声思考 - 如果驱动程序中的批处理支持存在问题,您可以尝试使用单个查询来实现相同的目的,从而使批处理的相关性降低。 (如您所知,批处理是为了避免多个查询的延迟,但即使批处理单个查询,延迟仍然存在。)
以下是如何使用单个查询实现乐观更新
由于您可以使用临时表作为选择查询,因此您可以找到将更新哪些行,然后将其作为更新查询提交。 (当然,所有这些都在一个事务内。)
为了说明:
这给出了所有要更新的数据的 id,您可以存储这些数据以供以后参考
然后可以在更新语句中使用相同的查询
Just thinking aloud here - if it's a problem with the batch support in the driver, you could try to achieve the same using a single query, making batching less relevant. (As you know, batching is about avoiding latency with multiple queries, but latency is still present even when batching a single query.)
Here's how you might achieve the optimistic update with a single query
Since you can use the temporary table as a select query, you can find which rows would be updated, and then submit this as an update query. (All within a transaction, of course.)
To illustrate:
This gives the ids of all data to be updated, which you can store for later reference
The same query can then be used in an update statement