MSSE SENG 5199

Course Materials for the MSSE Web Application Development Course

slidenumbers: true

JPA and Spring Data

Mike Calvo

mike@citronellasoftware.com


ORM


ORM Benefits


JPA


Core JPA Annotations


JPA Annotation Rules


Overriding Defaults


#Relationships


Relationship Features


Lazy Loading


Fetch


Cascade


Inheritance


Querying with JPA


JPAQL and HQL


Example JPAQL

select s from Song where s.title = ?

SELECT p FROM Player p WHERE p.name LIKE ’Mich%’

SELECT p FROM Player p WHERE p.teams IS EMPTY

SELECT DISTINCT a FROM Author a INNER JOIN a.books b WHERE b.publisher.name = 'XYZ Press'


JPAQL Supports Writes

UPDATE Player p SET p.status = 'inactive' WHERE p.lastPlayed < :inactiveThresholdDate DELETE FROM Player p WHERE p.status = 'inactive' AND p.teams IS EMPTY


Constraints via Java Validation


Example Constraints

@Entity
class Account {
  @Id
  Long id

  @NotNull @Email @Column(unique=true)
  String Email

  @NotNull @NotBlank
  String password
}

Spring Data


Repositories


Repository Types


Example Repository

interface UserRepository extends JpaRepository<User, Long> {
}

Finder Syntax

@Entity class Person {
  @Id Long id
  String firstName
  String lastName
}

interface PersonRepository<Person, Long> {
  List<Person> findByFirstName(String firstName)
  List<Person> findByFirstNameAndLastName(String firstName, String lastName)
}

Custom Queries

public interface UserRepository extends JpaRepository<User, Long> {

  @Query("select u from User u where u.firstname like %?1")
  List<User> findByFirstnameEndsWith(String firstname);
}

Projections


Projection Interface Example

interface FullNameAndCountry {

  @Value("#{target.firstName} #{target.lastName}")
  String getFullName();

  @Value("#{target.address.country}")
  String getCountry();
}

Criteria Queries


Example specification

public class CustomerSpecs {

  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(_Customer.createdAt), date)
      }
    };
  }
}

List<Customer> customers = customerRepository.findAll(CustomerSpecs.isLongTermCustomer());

Example Queries


Query By Example

Person person = new Person(firstName: 'Dave')                       

Example<Person> example = Example.of(person);

Adding Spring Data to Spring Boot

compile('org.springframework.boot:spring-boot-starter-data-jpa')