1. Обзор
API критериев JPA можно использовать для простого добавления нескольких И/ИЛИ условий при запросе записей в базе данных. В этом руководстве мы рассмотрим краткий пример запросов критериев JPA, которые объединяют несколько предикатов И/ИЛИ предикатов.
Если вы не знакомы с предикатами, мы рекомендуем сначала прочитать об основных запросах критериев JPA.
2. Пример приложения
Для наших примеров мы рассмотрим инвентаризацию Элемент сущности, каждая из которых имеет идентификатор, | имя , цвет и класс :
@Entity public class Item { @Id private Long id; private String color; private String grade; private String name; // standard getters and setters }
3. Объединение Двух Предикатов ИЛИ С Использованием Предиката И
Давайте рассмотрим случай использования, когда нам нужно найти элементы, имеющие оба:
- красный или синий цвет
И - Класс А или В
Мы можем легко сделать это с помощью API критериев JPA и() и или() составных предикатов .
Для начала давайте настроим ваш запрос:
CriteriaBuilder criteriaBuilder = entityManager.getCriteriaBuilder(); CriteriaQuery- criteriaQuery = criteriaBuilder.createQuery(Item.class); Root
- itemRoot = criteriaQuery.from(Item.class);
Теперь нам нужно будет построить Предикат , чтобы найти элементы, имеющие синий или красный цвет:
Predicate predicateForBlueColor = criteriaBuilder.equal(itemRoot.get("color"), "blue"); Predicate predicateForRedColor = criteriaBuilder.equal(itemRoot.get("color"), "red"); Predicate predicateForColor = criteriaBuilder.or(predicateForBlueColor, predicateForRedColor);
Далее, давайте построим Предикат , чтобы найти элементы класса A или B:
Predicate predicateForGradeA = criteriaBuilder.equal(itemRoot.get("grade"), "A"); Predicate predicateForGradeB = criteriaBuilder.equal(itemRoot.get("grade"), "B"); Predicate predicateForGrade = criteriaBuilder.or(predicateForGradeA, predicateForGradeB);
Наконец, мы определяем И Предикат из этих двух, применяем метод where() и выполняем наш запрос:
Predicate finalPredicate = criteriaBuilder.and(predicateForColor, predicateForGrade); criteriaQuery.where(finalPredicate); List- items = entityManager.createQuery(criteriaQuery).getResultList();
4. Объединение двух предикатов И С использованием Предиката ИЛИ
С другой стороны, давайте рассмотрим случай, когда нам нужно найти предметы, имеющие либо:
- красный цвет и класс D ИЛИ
- синий цвет и класс В
Логика довольно схожа, но здесь мы сначала создаем два И Предиката s, а затем объединяем их с помощью ИЛИ Предиката :
CriteriaBuilder criteriaBuilder = entityManager.getCriteriaBuilder(); CriteriaQuery- criteriaQuery = criteriaBuilder.createQuery(Item.class); Root
- itemRoot = criteriaQuery.from(Item.class); Predicate predicateForBlueColor = criteriaBuilder.equal(itemRoot.get("color"), "red"); Predicate predicateForGradeA = criteriaBuilder.equal(itemRoot.get("grade"), "D"); Predicate predicateForBlueColorAndGradeA = criteriaBuilder.and(predicateForBlueColor, predicateForGradeA); Predicate predicateForRedColor = criteriaBuilder.equal(itemRoot.get("color"), "blue"); Predicate predicateForGradeB = criteriaBuilder.equal(itemRoot.get("grade"), "B"); Predicate predicateForRedColorAndGradeB = criteriaBuilder.and(predicateForRedColor, predicateForGradeB); Predicate finalPredicate = criteriaBuilder .or(predicateForBlueColorAndGradeA, predicateForRedColorAndGradeB); criteriaQuery.where(finalPredicate); List
- items = entityManager.createQuery(criteriaQuery).getResultList();
5. Заключение
В этом уроке мы использовали API критериев JPA для реализации случаев использования, когда нам нужно было объединить И/ИЛИ предикаты.
Как обычно, полный исходный код, используемый для этого урока, находится на GitHub .