【发布时间】:2011-11-25 22:30:29
【问题描述】:
我正在尝试编写一个查询来根据聚合列计算排名列。该查询是作为 Hibernate Criteria 查询一部分的 SQLProjection。 这是我尝试过的:
String sqlProjection =
"(select count(*) from IPTStatistic stat2 where
max(s.powerRestarts) > max({alias}.powerRestarts)) as rank)";
ProjectionList list = Projections.projectionList();
list.add(Projections.sqlProjection(sqlRankQuery, new String[]{"rank"}, new Type[]{new IntegerType()})));
list.add(Property.forName("managedObjectName").group());
list.add(Projections.max("powerRestarts").as("maxRestarts"));
Criteria crit = hibernateSessionHelper.getSessionFactory().getCurrentSession().createCriteria(IPTStatistic.class);
crit.setProjection(projection);
crit.list();
当我在 SQL 投影中使用非聚合列时,子选择有效并且我得到了预期的结果,只有在我引入 max() 时才会发生错误。
这会引发一个相当非特定的org.hibernate.exception.GenericJDBCException,并带有消息“Could not execute query”。
日志显示:
WARN logExceptions, SQL Error: -458, SQLState: S1000
ERROR logExceptions, java.lang.NullPointerException java.lang.NullPointerException
我无法从上述错误消息中自己查明查询中的问题,谁能给我一些关于如何更正我的查询的指示?
更新:
我现在根据 axtavt 的回答使用以下 sqlProjection:
String sqlProjection = "(select count(*) from " +
"(select name from IPTStatistic s group by s.name " +
" having max(s.powerRestarts) > max({alias}.powerRestarts)) " +
"as r) as rank"
Hibernate生成的SQL是:
select (select count(*) from (select iptManagedObjectName from IPTStatistic s group by s.iptManagedObjectName having max(s.powerRestarts) > max(this_.powerRestarts)) as r) as rank, this_.iptManagedObjectName as y1_, from IPTStatistic this_
我现在收到错误:
WARN logExceptions, SQL Error: -5581, SQLState: 42581
ERROR logExceptions, unexpected token: SELECT
如果我删除 max({alias}.powerRestarts) 并将其替换为常量或 max(s.powerRestarts),则查询有效(但显然无法正确计算排名)。
在此 sqlProjection 查询中使用 {alias} 似乎有问题 - 可能与嵌套子查询有关 - 谁能帮忙?
谢谢。
【问题讨论】:
标签: hibernate hql criteria aggregation hibernate-criteria