java - Hibernate 为 Oracle 生成导致 ORA-02014 的查询

标签 java oracle hibernate jpa

我的项目使用 Hibernate 版本 4.0.1.Final 和 JPA 2.0。我需要更改一个 HQL - 添加顺序,看起来很简单,只是它现在以 SQL 语法错误结尾。

我已经定义了这个 HQL 命名查询:

SELECT s FROM Entity s WHERE s.status = :status ORDER BY s.priority, s.startDate

-> Bold 是我要添加的部分。

现在因为这个命名查询是用锁执行的 - LockModeType.PESSIMISTIC_WRITE 它为 Oracle 的更新选择创建:

select *
  from (select entity.field 

  ...more fields...

          from DB_TABLE entity
         where (entity.STATUS = ?)
         order by entity.PRIORITY, entity.DISTRIB_START_DATE)
 where rownum <= ?
   for update

这个查询以

结尾

java.sql.SQLSyntaxErrorException: ORA-02014 cannot select FOR UPDATE from view with DISTINCT, GROUP BY

没有订单部分它工作正常。

有什么办法可以克服这个问题吗?我只需要按顺序选择那些记录。也不能在应用程序中对它们进行排序,因为它只选择了表格的一部分。

我尝试将 Hibernate 更新到 4.2.21.Final,但结果是一样的。 Hibernate 4.3+ 需要我不使用的 JPA2.1。
也许这是 Hibernate 的错误?

最佳答案

不,这不是 Hibernate 错误,这是您必须在 Oracle 中结合 rownum 进行排序的方式。参见 this article了解更多详情。

基本上,这意味着您不能在 Oracle 中的同一查询中组合排序、rownumselect for update

您必须将其分解为更多查询,具体方法取决于您的具体要求。例如:

1) 选择具有分页排序的实体的ids:

SELECT s.id FROM Entity s WHERE s.status = :status ORDER BY s.priority, s.startDate

2) 使用获得的ids选择具有锁定的实体:

SELECT s FROM Entity s WHERE s.id in :ids AND s.status = :status

3) 如果所选实体的数量少于 id 的数量,则同时条件发生变化(状态发生变化),继续处理锁定的实例或回滚并重试整个事务。

关于java - Hibernate 为 Oracle 生成导致 ORA-02014 的查询,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35017754/

相关文章:

java - @Transactional 在 Spring Web MVC 中不起作用?

java - 使用 EntityManager 验证实体的唯一性

java - 在 Hibernate 中执行 Criteria 查询后是否需要提交/关闭 session ?

java - 根据两列对二维数组进行排序

java - java中如何将二进制文件转换为对象

java - 将 dropwizard 项目部署到 heroku 时 yaml 中的 "Unrecognized Field: http"

bash - 从 PL/SQL Developer 和 SQL*plus 调用时,存储过程没有相同的结果

sql - 如何在 Oracle 中通过 XPath 获取第一个元素

java - 无法获取类路径资源的资源路径

oracle - Windows 找不到 'http:/.127.0.0.1:%HTTPPORT%/apex/f?p=4950' 。请确保您输入的名称正确无误,然后重试