Вопрос:
У меня есть таблица ROOT и таблица CHILDREN, которая содержит строки, относящиеся к ROOT.
Я хотел бы получить для каждой строки ROOT, объект, содержащий объект ROOT, и количество строк, связанных с ROOT.id в таблице CHILDREN.
Этого можно добиться довольно легко в SQL, но мне интересно, как писать это в JPQL
В SQL:
SELECT r.*, (SELECT COUNT(c.i_id) FROM children c WHERE c.rootId = r.id) FROM root r;
Я попытался переписать его в JPA, но он продолжает терпеть неудачу со следующей ошибкой
Caused by: org.hibernate.HibernateException: Errors in named queries: xxx Caused by: org.hibernate.hql.internal.ast.QuerySyntaxException: Unable to locate appropriate constructor on class RootExtended…
Класс Java:
package plop; public class RootExtended{ private Root root; private Long count; public RootExtended(final Root root, final Long count) { this.root= root; this.count= count; } // getters and setters to follow }
JPQL:
SELECT new plop.RootExtended(r, (SELECT count(c.id) FROM Child as c WHERE c.rootId = r.id ) ) FROM Root as r
Есть идеи?
Ответ №1
Я думаю, вам не разрешено использовать подзапросы в части SELECT в JPA (по крайней мере, версии <= 2), поскольку они ограничены предложениями WHERE и HAVING. См. Это для деталей.
В качестве решения вы могли бы сделать два запроса, во втором сделать COUNT() и загрузить его в код в экземпляры ExtendedRoot.
Ответ №2
Класс:
public class RootExtended{ private Root root; private Long count; public RootExtended(final Root root, final Long count) { this.root= root; this.count= count; } // getters and setters to follow }
Запрос:
SELECT NEW package.RootExtended ( rt.r, rt.cnt) from ( select r from Root r, (SELECT count(c.id) as cnt FROM Child c WHERE c.rootId = r.id ) rt )