#java #hibernate #hibernate-criteria
#java #гибернация #переход в спящий режим-критерии
Вопрос:
По умолчанию, когда выполняется count с помощью hibernate, он генерирует count (*) , возможно ли изменить его так, чтобы значение по умолчанию стало count (1) ? я не хочу использовать HQL для этого. Я имею в виду при использовании criteria.setProjection(Projections.rowCount());
Комментарии:
1. Почему вы хотели бы сделать такую вещь?
Ответ №1:
Вы можете создать свою пользовательскую функцию подсчета, реализовав интерфейс StandartSQLFuction. Затем вам нужно создать подкласс используемого вами диалектного класса и зарегистрировать вашу функцию в конструкторе с помощью метода registerFunction.
Комментарии:
1. ну, я не хочу создавать отдельный sql. вместо этого при использовании criterions.setProjection(Projections.rowCount());
2. Да, это то, что я говорю. И чтобы заставить эту конструкцию работать, вы должны изменить существующий диалект. Посмотрите, что делает Projections.rowCount: он берет объект, представляющий функцию SQL count, из репозитория и отображает его. Вы хотите изменить поведение по умолчанию, поэтому вам нужно создать собственную функцию и зарегистрировать ее. Чтобы зарегистрировать его, вы должны создать подкласс некоторого диалекта. Вы можете назвать тот же параметр — count, и он переопределит определение по умолчанию.
3. Или вы можете создать собственную проекцию. Просто взгляните хотя бы на исходные коды Hibernate. По крайней мере, в коде проектирования: класс RowCountProjection каждый раз заменяет ‘*’ в поле count. Если вы хотите использовать стандартную проекцию, вам нужно создать новую функцию, которая будет игнорировать аргументы. Это так просто, просто просмотрите исходные тексты.
Ответ №2:
Если в вашем запросе есть GROUP BY, вы можете использовать метод sqlGroupProjection() в классе theProjections. Он принимает четыре аргумента, первым из которых является предложение select запроса. В этом первом аргументе вы можете определить count(1) вместо count(*). Например:
Criteria criteria = sessionFactory.getCurrentSession().createCriteria(EventLog.class, "event")
.createAlias("site", "site").setProjection(Projections.projectionList()
.add(Projections.sqlGroupProjection("var_val1,count(1) as count",
"var_val1",
new String[]{"var_val1", "count"},
new Type[]{Hibernate.STRING, Hibernate.INTEGER})))
.add(Restrictions.ge("event.date_time", strFrom))
.add(Restrictions.eq("site.companyID", custid))