Problème :
Les référentiels JPA Spring Data prennent en charge la création de requêtes avec des paramètres fixes et prédéfinis paramètres. Cependant, il est nécessaire de générer dynamiquement des requêtes avec des clauses AND arbitraires basées sur des champs fournis par l'utilisateur. Cette approche est peu évolutive et nécessite une définition de requête explicite pour chaque combinaison possible.
Meilleure approche : spécifications avec l'API Criteria
Spring Data fournit des spécifications qui exploitent l'API Criteria pour créer des spécifications flexibles et dynamiques. requêtes. En étendant l'interface du référentiel avec JpaSpecificationExecutor, il est possible d'exécuter des spécifications à l'aide de diverses méthodes, notamment findAll.
Interface de spécifications :
public interface Specification<T> { Predicate toPredicate(Root<T> root, CriteriaQuery<?> query, CriteriaBuilder builder); }
Exemple d'implémentation :
public static Specification<Customer> isLongTermCustomer() { return new Specification<Customer>() { public Predicate toPredicate(Root<Customer> root, CriteriaQuery<?> query, CriteriaBuilder builder) { LocalDate date = new LocalDate().minusYears(2); return builder.lessThan(root.get('dateField'), date); } }; } public static Specification<Customer> hasSalesOfMoreThan(MontaryAmount value) { return new Specification<Customer>() { public Predicate toPredicate(Root<T> root, CriteriaQuery<?> query, CriteriaBuilder builder) { // build query here } }; }
Exemple Utilisation :
List customers = customerRepository.findAll(isLongTermCustomer()); MonetaryAmount amount = new MonetaryAmount(200.0, Currencies.DOLLAR); List<Customer> customers = customerRepository.findAll( where(isLongTermCustomer()).or(hasSalesOfMoreThan(amount)));
Spécifications complexes :
Pour les spécifications complexes, vous pouvez définir des méthodes personnalisées dans votre classe de spécifications :
public static Specification<WorkInProgress> findByCriteria(final SearchCriteria searchCriteria) { return new Specification<WorkInProgress>() { public Predicate toPredicate(Root<WorkInProgress> root, CriteriaQuery<?> query, CriteriaBuilder cb) { List<Predicate> predicates = new ArrayList<Predicate>(); // Add predicates based on search criteria return cb.and(predicates.toArray(new Predicate[] {})); } }; }
Conclusion :
Les spécifications permettent la génération de requêtes dynamiques sans avoir besoin d'une définition explicite de requête. Cette approche est évolutive et extensible, simplifiant la création de requêtes flexibles et personnalisables. Reportez-vous à la documentation des référentiels JPA pour plus d'informations.
Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!