Bevezetés a Criteria API-ba

Kétféleképpen írhat adatbázis-lekérdezéseket hibernált állapotban:

  • Hibernált lekérdezési nyelv
  • Criteria API

Az elsővel már régen találkoztál, itt az ideje, hogy megismerkedj a Criteria API-val. Ez egy nagyon hatékony eszköz, valamikor még népszerűbb volt, mint a HQL. Ma már nem annyira népszerű, de bizonyos feladatokra biztosan jobb megoldás lesz, mint a HQL.

Mindenesetre nem tanulhatja meg a hibernálást anélkül, hogy megismerné a Criteria API-t. Írjunk egy kis példát, majd elemezzük. Például az összes alkalmazottat (Alkalmazottat) lekérjük az adatbázisból. A következőket kapjuk:

CriteriaBuilder builder = session.getCriteriaBuilder();
CriteriaQuery<Employee> critQuery = builder.createQuery(Employee.class);

Root<Employee> root = critQuery.from(Employee.class);
critQuery.select(root);

Query<Employee> query = session.createQuery(critQuery);
List<Employee> results = query.getResultList();

Bonyolultnak tűnik. Összehasonlításképpen írjuk le ugyanazt a HQL lekérdezést:

String hqlQuery = "from Employee";

Query<Employee> query = session.createQuery(hqlQuery);
List<Employee> results = query.getResultList();

Megjegyzendő, hogy mindkét példa utolsó két sora majdnem teljesen megegyezik: létrehozunk egy Query objektumot, és azt használjuk a lista létrehozásához. Ez arra utal, hogy a többi sor valami hasonlót csinál.

Nézd meg az első példa 3. és 4. sorát:

Root<Employee> root = critQuery.from(Employee.class);
critQuery.select(root);

Írjuk őket egy sorba:

critQuery.select(critQuery.from(Employee.class));

Nem emlékeztet semmire? És ha kicsit másképp színezed:

critQuery.select(critQuery.from(Employee.class));

Igen, ez a SELECT FROM lekérdezés bonyolult felépítése.

Példák a Criteria API-val való munkára

A jobb megértés érdekében csak néhány példát mondok.

1. kérés . Minden 10 ezret meghaladó fizetésű alkalmazottat kap:

critQuery.select(critQuery.from(Employee.class)).where(builder.gt(root.get("salary"), 10000));

2. kérés . Szerezzen meg minden alkalmazottat, akinek fizetése kevesebb, mint 50 ezer:

critQuery.select(critQuery.from(Employee.class)).where(builder.lt(root.get("salary"), 50000));

3. kérés . Szerezzen be minden olyan alkalmazottat, akinek a beosztása tartalmazza a „teszt” szót:

critQuery.select(critQuery.from(Employee.class)).where(builder.like(root.get("occupation"), "%test%"));

4. kérés . Kapjon minden alkalmazottat 10-50 ezer fizetéssel:

critQuery.select(critQuery.from(Employee.class)).where(builder.between(root.get("salary"), 10000, 50000));

5. kérés . Szerezzen be minden alkalmazottat, akinek a neve null:

critQuery.select(critQuery.from(Employee.class)).where(builder.isNull(root.get("name")));

6. kérés . Szerezzen be minden alkalmazottat, akinek a neve nem null:

critQuery.select(critQuery.from(Employee.class)).where(builder.isNotNull(root.get("name")));

Ez egy ilyen trükkös módja a lekérdezés felépítésének:

  • Először megkapja a tárgyatCriteriaBuilder.
  • Ezután használja objektum létrehozásáhozCriteriaQuery.
  • Ezután elkezdi hozzáadni az alkatrészeket hozzáCriteriaQueryÉsCriteriaBuilder.

Így állíthatja be a paramétereket:

  • KIVÁLASZTÁS
  • TÓL TŐL
  • AHOL

Használata isCriteriaBuilderkülönböző feltételeket szerkeszthet a WHERE számára.

Haladó munka a Criteria API-val

A Criteria API használatával bármilyen bonyolultságú lekérdezést készíthet. És ez nagyszerű hír. Például egy összetett WHERE záradékot szeretne. Íme, hogyan kell csinálni:

Predicate greaterThan = builder.gt(root.get("salary"), 1000);
Predicate testers = builder.like(root.get("occupation"), "test%");

critQuery.select(critQuery.from(Employee.class)).where(builder.or(greaterThan, testers));

Ha VAGY helyett ÉS-t szeretne írni, akkor csak az utolsó sort kell módosítania:

critQuery.select(critQuery.from(Employee.class)).where(builder.and(greaterThan, testers));

Valójában minden nagyon egyszerű. Hadd adjak egy táblázatot néhány összehasonlítással:

SQL Módszer Teljes rekord
a<b lt(a, b) builder.lt(a, b)
a > b gt(a, b) builder.gt(a, b)
a VAGY b vagy(a,b) építő.or(a, b)
a ÉS b és (a, b) builder.and(a,b)
a LIKE b mint (a,b) builder.like(a, b)
a BETWEEN (c, d) (a, c, d) között builder.between(a, c, d)
a IS NULL isNull(a) builder.isNull(a)
a NEM NULL isNotNull(a) builder.isNotNull(a)

Minden egyszerű, nem?

És hogyan adjunk rendezést a lekérdezéshez? Nagyon egyszerű:

critQuery.select( critQuery.from(Employee.class) );
critQuery.where( builder.and(greaterThan, testers) );
critQuery.orderBy( builder.asc(root.get("salary"), builder.desc(root.get("joinDate") )

Csak hívja a tárgyatCriteriaQueryorderBy() metódussal , és adja át neki a szükséges paramétereket.

Így nézne ki ugyanaz a lekérdezés HQL-ben. Összehasonlítás:

select * from Employee
where (…) and (…)
order by 'salary' asc, 'joinDate' desc

Csak 3 dolgot kell emlékezned:

  • Az olyan kulcsoperátorok, mint a SELECT, FROM, WHERE, meghívásra kerülnek egy objektumonCriteriaQuery.
  • A segédoperátorok, mint például az AND, OR, DESC, meghívásra kerülnek az objektumonCriteriaBuilder.
  • A mezőnevek az objektumból a get()gyökér.