Ressources

Types d’opĂ©ration

Il n’est possible de rĂ©aliser que trois types d’opĂ©rations avec l’API Criteria qui sont la lecture, la modification et la suppression (SELECT, UPDATE et DELETE). Chacune de ces opĂ©rations a ses propres classes qui sont :

  • CriteriaQuery pour le SELECT.
  • CriteriaUpdate pour l’UPDATE.
  • CriteriaDelete pour le DELETE.

La classe CriteriaBuilder

La classe CriteriaBuilder est le principal point d’entrĂ©e de l’API Criteria. Elle fournit des mĂ©thodes pour crĂ©er les Ă©lĂ©ments fondamentaux d’une requĂȘte, notamment :

  • createQuery() : CrĂ©e une instance de CriteriaQuery pour dĂ©finir la requĂȘte.
  • equal(), greaterThan(), like(), etc. : CrĂ©ent des prĂ©dicats pour filtrer les donnĂ©es.
  • sum(), avg(), max(), etc. : CrĂ©ent des expressions d’agrĂ©gation.
CriteriaBuilder cb = em.getCriteriaBuilder();  // Créer un CriteriaBuilder depuis EntityManager
CriteriaQuery<Pet> cq = cb.createQuery(Pet.class); // Utiliser le CB pour crĂ©er une requĂȘte

La classe CriteriaQuery

La classe CriteriaQuery reprĂ©sente la requĂȘte en elle-mĂȘme et permet de dĂ©finir les diffĂ©rents Ă©lĂ©ments constitutifs de la requĂȘte, tels que :

  • DĂ©finition de la source (.from()) : elle renvoie un objet Root, qui reprĂ©sente cette entitĂ© dans la requĂȘte et permet d’accĂ©der aux attributs de celle-ci.
  • Les sĂ©lections (.select()) : pour dĂ©finir les champs Ă  rĂ©cupĂ©rer.
  • Les filtres (.where()) : pour appliquer des conditions de filtrage.
  • Les jointures (.join()) : pour lier plusieurs entitĂ©s.
  • Les tris (.orderBy()) : pour ordonner les rĂ©sultats.
  • Les agrĂ©gations (.groupBy(), .having()) : pour grouper et appliquer des conditions sur les groupes.
Root<Pet> pet = cq.from(Pet.class);
cq.select(pet);

Une fois la requĂȘte construite, elle peut ĂȘtre exĂ©cutĂ©e via l’EntityManager.

TypedQuery<Pet> q = em.createQuery(cq);
List<Pet> allPets = q.getResultList(); // permet d'exĂ©cuter la requĂȘte

Les expressions de prédicats

Les expressions de prĂ©dicats sont les Ă©lĂ©ments de base pour dĂ©finir les conditions de filtrage dans une requĂȘte Criteria. Voici quelques exemples d’utilisation :

  • cb.equal(root.get("name"), "John") : Filtre les entitĂ©s oĂč le champ name est Ă©gal Ă  “John”.
  • cb.greaterThan(root.get("age"), 18) : Filtre les entitĂ©s oĂč l’age est supĂ©rieur Ă  18.
  • cb.like(root.get("email"), "%@example.com") : Filtre les entitĂ©s dont l’email se termine par “@example.com”.
  • cb.isNull(root.get("address")) : Filtre les entitĂ©s oĂč l’address est null.

Ces prĂ©dicats peuvent ĂȘtre combinĂ©s avec des opĂ©rateurs logiques (and(), or(), not()) pour crĂ©er des conditions de filtrage complexes.

Exemple select

// Créer un objet de type CriteriaQuery
CriteriaBuilder cb = em.getCriteriaBuilder();
CriteriaQuery<Pet> cq = cb.createQuery(Pet.class);
 
// Construire la requĂȘte
Root<Pet> pet = cq.from(Pet.class);
Join<Pet, Owner> owner = pet.join("owner");
 
cq.select(pet)
  .where(
    cb.equal(pet.get("type"), "dog"),
    cb.lessThan(pet.get("age"), 5),
    cb.equal(owner.get("id"), ownerId)
  )
  .orderBy(cb.asc(pet.get("name")));
 
// Executer la requĂȘte
TypedQuery<Pet> q = em.createQuery(cq);
List<Pet> filteredPets = q.getResultList();

Exemple update

Attention

A toujours exécuter le code dans une transaction

// Start a transaction
em.getTransaction().begin();
 
// Create CriteriaBuilder and CriteriaUpdate
CriteriaBuilder cb = em.getCriteriaBuilder();
CriteriaUpdate<Pet> update = cb.createCriteriaUpdate(Pet.class);
 
// Define the root entity (Pet)
Root<Pet> pet = update.from(Pet.class);
 
// Join with Owner
Join<Pet, Owner> owner = pet.join("owner");
 
// Set the update: increase age by 1
update.set(pet.get("age"), cb.sum(pet.get("age"), 1))
      .where(
          cb.equal(pet.get("type"), "dog"),
          cb.lessThan(pet.get("age"), 5),
          cb.equal(owner.get("id"), ownerId)
      );
 
// Execute the update
Query query = em.createQuery(update);
int updatedCount = query.executeUpdate();
 
// Commit transaction
em.getTransaction().commit();