From b971f411550769396244582e30d1fc4ab0da64ea Mon Sep 17 00:00:00 2001 From: Gustavo Martin Morcuende Date: Mon, 11 Jul 2016 22:00:41 +0200 Subject: [PATCH] SpringJPA: Querydsl VS Spring Specifications Querydsl is easier than Specifications and JPA Criterias. --- .../domain/specifications/AdSpectifications.java | 42 ++++++++++++++++++++++ .../persistence/repository/AdRepository.java | 3 +- .../java/de/spring/example/services/AdService.java | 12 +++++++ .../services/impl/AdDescriptionServiceImpl.java | 6 ++++ .../example/services/impl/AdServiceImpl.java | 41 +++++++++++++++++++++ 5 files changed, 103 insertions(+), 1 deletion(-) create mode 100644 SpringJava/JPA/src/main/java/de/spring/example/persistence/domain/specifications/AdSpectifications.java create mode 100644 SpringJava/JPA/src/main/java/de/spring/example/services/AdService.java create mode 100644 SpringJava/JPA/src/main/java/de/spring/example/services/impl/AdServiceImpl.java diff --git a/SpringJava/JPA/src/main/java/de/spring/example/persistence/domain/specifications/AdSpectifications.java b/SpringJava/JPA/src/main/java/de/spring/example/persistence/domain/specifications/AdSpectifications.java new file mode 100644 index 0000000..6ee3644 --- /dev/null +++ b/SpringJava/JPA/src/main/java/de/spring/example/persistence/domain/specifications/AdSpectifications.java @@ -0,0 +1,42 @@ +package de.spring.example.persistence.domain.specifications; + +import java.time.LocalDate; + +import javax.persistence.criteria.CriteriaBuilder; +import javax.persistence.criteria.CriteriaQuery; +import javax.persistence.criteria.Predicate; +import javax.persistence.criteria.Root; + +import org.springframework.data.jpa.domain.Specification; + +import de.spring.example.persistence.domain.Ad; + +public class AdSpectifications { + + public static Specification createdToday() { + return new Specification() { + + @Override + public Predicate toPredicate(Root root, CriteriaQuery query, CriteriaBuilder cb) { + final LocalDate date = LocalDate.now(); + + return cb.equal(root.get("createdAt"), date); + } + + }; + + } + + public static Specification mobileImage(String image) { + return new Specification() { + + @Override + public Predicate toPredicate(Root root, CriteriaQuery query, CriteriaBuilder cb) { + + return cb.equal(root.get("adMobileImage"), image); + } + + }; + + } +} diff --git a/SpringJava/JPA/src/main/java/de/spring/example/persistence/repository/AdRepository.java b/SpringJava/JPA/src/main/java/de/spring/example/persistence/repository/AdRepository.java index 592e241..bc73359 100644 --- a/SpringJava/JPA/src/main/java/de/spring/example/persistence/repository/AdRepository.java +++ b/SpringJava/JPA/src/main/java/de/spring/example/persistence/repository/AdRepository.java @@ -1,5 +1,6 @@ package de.spring.example.persistence.repository; +import org.springframework.data.jpa.repository.JpaSpecificationExecutor; import org.springframework.data.jpa.repository.Query; import org.springframework.data.repository.PagingAndSortingRepository; import org.springframework.data.repository.query.Param; @@ -13,7 +14,7 @@ import de.spring.example.persistence.domain.Ad; * Be careful with @Transactional. SimpleJpaRepository has annotated methods. * */ -public interface AdRepository extends PagingAndSortingRepository { +public interface AdRepository extends PagingAndSortingRepository, JpaSpecificationExecutor { // Named Native Query (using the native language of the store) It is not portable. // See de.spring.persistence.example.domain.Ad diff --git a/SpringJava/JPA/src/main/java/de/spring/example/services/AdService.java b/SpringJava/JPA/src/main/java/de/spring/example/services/AdService.java new file mode 100644 index 0000000..c491be8 --- /dev/null +++ b/SpringJava/JPA/src/main/java/de/spring/example/services/AdService.java @@ -0,0 +1,12 @@ +package de.spring.example.services; + +import org.resthub.common.service.CrudService; +import org.springframework.data.domain.Page; +import org.springframework.data.domain.Pageable; + +import de.spring.example.persistence.domain.Ad; + +public interface AdService extends CrudService { + + public Page queryCriteriaExample(Pageable pageRequest); +} diff --git a/SpringJava/JPA/src/main/java/de/spring/example/services/impl/AdDescriptionServiceImpl.java b/SpringJava/JPA/src/main/java/de/spring/example/services/impl/AdDescriptionServiceImpl.java index 6218840..7f5a681 100644 --- a/SpringJava/JPA/src/main/java/de/spring/example/services/impl/AdDescriptionServiceImpl.java +++ b/SpringJava/JPA/src/main/java/de/spring/example/services/impl/AdDescriptionServiceImpl.java @@ -33,6 +33,12 @@ public class AdDescriptionServiceImpl /** * Using Querydsl. Giving some business logic to this service :) + * + * Querydsl: fluent interface done easy. There is no effort because it is already implemented. + * + * Criteria using Specifications requires some effort. + * + * See: de.spring.example.services.impl.AdServiceImpl */ @Override public Page queryDslExample(Pageable pageRequest) { diff --git a/SpringJava/JPA/src/main/java/de/spring/example/services/impl/AdServiceImpl.java b/SpringJava/JPA/src/main/java/de/spring/example/services/impl/AdServiceImpl.java new file mode 100644 index 0000000..619fcb2 --- /dev/null +++ b/SpringJava/JPA/src/main/java/de/spring/example/services/impl/AdServiceImpl.java @@ -0,0 +1,41 @@ +package de.spring.example.services.impl; + +import static org.springframework.data.jpa.domain.Specifications.where; + +import javax.inject.Inject; + +import org.resthub.common.service.CrudServiceImpl; +import org.springframework.data.domain.Page; +import org.springframework.data.domain.Pageable; + +import de.spring.example.persistence.domain.Ad; +import de.spring.example.persistence.domain.specifications.AdSpectifications; +import de.spring.example.persistence.repository.AdRepository; +import de.spring.example.services.AdService; + +public class AdServiceImpl + extends CrudServiceImpl + implements AdService { + + @Override + @Inject + public void setRepository(AdRepository repository) { + this.repository = repository; + } + + /** + * Criteria using Specifications. + * + * It is more complicated that when using Querydsl because I have to implement the + * Specifications. Querydsl is doing everything for me. + * + * See: de.spring.example.services.impl.AdDescriptionServiceImpl + */ + @Override + public Page queryCriteriaExample(Pageable pageRequest) { + return repository.findAll( + where(AdSpectifications.createdToday()).and(AdSpectifications.mobileImage("picasso")), + pageRequest); + } + +} -- 2.1.4