Hands On Spring Data

Eric Bottard, Developer Advocate, VMware
@ebottard
Florent Biville, Developer, Lateral Thoughts
@fbiville



© 2012 SpringSource, by VMware
Eric BOTTARD


• Developer Advocate VMware
•   @ebottard
•   ebottard@vmware.com




2
Florent BIVILLE


• Développeur chez LateralThoughts
•   @fbiville




3
“   Spring Data is an umbrella project which
    aims to provide a familiar and consistent
    Spring-based programming model for for
    new datastores while retaining store-
    specific features and capabilities
Relational




JDBC
JPA
Document store




MongoDB
CouchDB
Column oriented




HBase
Cassandra
Graph




Neo4j
OrientDB
Data Grids




GemFire
Coherence
Terracotta
Key Value




Redis
Riak
Big Data




Hadoop
Templates
Mapping
Mapping


• Tells the framework how to store object properties and
  relationships
• Favors convention over configuration
• Does not try to shoehorn one model into another (e.g.
  does not use JPA annotations for Mongo)




14
Example: MongoDB
@Document
@CompoundIndexes({
    @CompoundIndex(name = "age_idx", def = "{'lastName': 1, 'age': -1}")
})
public class Person<T extends Address> {

  @Id
  private String id;

  @Indexed(unique = true)
  private Integer ssn;

  @Field("fName")
  private String firstName;

  @Indexed
  private String lastName;

  @Transient
  private Integer accountTotal;

  @DBRef
  private List<Account> accounts;

  private T address;
Repositories
Repositories


public interface PersonRepository
    extends CrudRepository<User, Long> {

       …

}

No implementation needed!
Magic Finders
Magic Finders
public interface PersonRepository extends Repository<User, Long> {

 List<Person> findByEmailAddressAndLastname(EmailAddress emailAddress, String
lastname);

  // Enables the distinct flag for the query
  List<Person> findDistinctPeopleByLastnameOrFirstname(String lastname, String
firstname);
  List<Person> findPeopleDistinctByLastnameOrFirstname(String lastname, String
firstname);

  // Enabling ignoring case for an individual property
  List<Person> findByLastnameIgnoreCase(String lastname);
  // Enabling ignoring case for all suitable properties
  List<Person> findByLastnameAndFirstnameAllIgnoreCase(String lastname, String
firstname);

    // Enabling static ORDER BY for a query
    List<Person> findByLastnameOrderByFirstnameAsc(String lastname);
    List<Person> findByLastnameOrderByFirstnameDesc(String lastname);
}
Pagination
Pagination and Dynamic Ordering


public interface PersonRepository
    extends CrudRepository<User, Long> {

    Page<User> findByLastname(String lastname, Pageable pageable);




    List<User> findByLastname(String lastname, Sort sort);

    // NOTE: Pageable embeds a Sort


}
Qu eries
Explicit Queries


public interface ProductsRepository extends JpaRepository<Product, Long> {

	   @Query(value = "select p from Product p order by p.rating desc",
       countQuery = "select count(p) from Product p")
	   Page<Product> findTopRated(Pageable pageable);
}
Cross Store support
Query DSL Integration
REST
REST Shell
Customization
JSON
Mongo DB - schema-less document DB

databases
mongo> show dbs;
  myDatabase 0.3046578 GB
mongo> use myDatabase;

  collections
  mongo> show collections;
    rockCollection
    colleagueSean
  mongo> db.rockCollection.find().pretty(); // last call “prettifies” output

     documents
     mongo> db.rockCollection.find({name:"The Beatles"}).pretty();
       {"_id" : ObjectId("50b7d870744e5ef5eee5224e"),
       "_class" : "xxx.music.domain.Band",
       "name" : "The Beatles",
       [...] }
MongoDB: Queries as JSON documents



db.inventory.find({
 price:1.99,
 $or: [
   { qty: { $lt: 20 } },
   { sale: true }
 ]
})
GridFS - can I haz large objectz?
• mongo> show collections;
     – fs.chunks
     – fs.files
• CHUNKS
     – 256KB portion of a Mongo object (a.k.a. file), stored into
       collection “fs.chunks”
• FILES
     – Metadata about the file stored into “fs.files”: filename, content
       type ...


• Spring Data brings
     – GridFsTemplate
     – GridFsResource (wraps GridFSDBFile)

33
Nodes & Relationships




35
Nodes


                                                   NoSQL
 Spring        HELPS_WITH                    standsFor: "Not Only
  Data         how: "it roxx"                       SQL"




IS_PART_OF
                                Properties

             Relationship


    Spring
Cypher
Neo4J - Cypher Query Language

start doctor=node:characters(character = 'Doctor')
match (doctor)<-[:COMPANION_OF]-(companion)
    -[:APPEARED_IN]->(episode)
return companion.character, count(episode)
order by count(episode) desc
limit 5
Image credits

•    keys http://www.sxc.hu/photo/1381979
•    spiderweb http://www.sxc.hu/photo/1309629
•    columns http://www.sxc.hu/photo/511217
•    documents http://www.sxc.hu/photo/913588
•    umbrella http://www.sxc.hu/photo/1182110
•    nail http://www.sxc.hu/photo/1101239
•    relational http://www.sxc.hu/photo/541351
•    callback http://www.sxc.hu/photo/1134440
•    repositories http://www.sxc.hu/photo/1352633
•    pagination http://www.sxc.hu/photo/830250
•    magic http://www.sxc.hu/photo/829135
•    cypher http://www.sxc.hu/photo/1118342
•    mapping http://www.sxc.hu/photo/1147986
•    grid http://www.sxc.hu/photo/1222068
•    elephant http://www.sxc.hu/photo/1168187
•    cross knot http://www.sxc.hu/photo/1396427
•    rope knot http://www.sxc.hu/photo/1181983
•    married http://www.sxc.hu/photo/937988
•    shell http://www.sxc.hu/photo/866402
•    diesel http://www.sxc.hu/photo/1076436
•    car tuning http://www.sxc.hu/photo/5877
•    rest on couch: If you haven’t, go watch Fight Club. NOW.



39

Hands On Spring Data

  • 1.
    Hands On SpringData Eric Bottard, Developer Advocate, VMware @ebottard Florent Biville, Developer, Lateral Thoughts @fbiville © 2012 SpringSource, by VMware
  • 2.
    Eric BOTTARD • DeveloperAdvocate VMware • @ebottard • ebottard@vmware.com 2
  • 3.
    Florent BIVILLE • Développeurchez LateralThoughts • @fbiville 3
  • 4.
    Spring Data is an umbrella project which aims to provide a familiar and consistent Spring-based programming model for for new datastores while retaining store- specific features and capabilities
  • 5.
  • 6.
  • 7.
  • 8.
  • 9.
  • 10.
  • 11.
  • 12.
  • 13.
  • 14.
    Mapping • Tells theframework how to store object properties and relationships • Favors convention over configuration • Does not try to shoehorn one model into another (e.g. does not use JPA annotations for Mongo) 14
  • 15.
    Example: MongoDB @Document @CompoundIndexes({ @CompoundIndex(name = "age_idx", def = "{'lastName': 1, 'age': -1}") }) public class Person<T extends Address> { @Id private String id; @Indexed(unique = true) private Integer ssn; @Field("fName") private String firstName; @Indexed private String lastName; @Transient private Integer accountTotal; @DBRef private List<Account> accounts; private T address;
  • 16.
  • 17.
    Repositories public interface PersonRepository extends CrudRepository<User, Long> { … } No implementation needed!
  • 18.
  • 19.
    Magic Finders public interfacePersonRepository extends Repository<User, Long> { List<Person> findByEmailAddressAndLastname(EmailAddress emailAddress, String lastname); // Enables the distinct flag for the query List<Person> findDistinctPeopleByLastnameOrFirstname(String lastname, String firstname); List<Person> findPeopleDistinctByLastnameOrFirstname(String lastname, String firstname); // Enabling ignoring case for an individual property List<Person> findByLastnameIgnoreCase(String lastname); // Enabling ignoring case for all suitable properties List<Person> findByLastnameAndFirstnameAllIgnoreCase(String lastname, String firstname); // Enabling static ORDER BY for a query List<Person> findByLastnameOrderByFirstnameAsc(String lastname); List<Person> findByLastnameOrderByFirstnameDesc(String lastname); }
  • 20.
  • 21.
    Pagination and DynamicOrdering public interface PersonRepository extends CrudRepository<User, Long> { Page<User> findByLastname(String lastname, Pageable pageable); List<User> findByLastname(String lastname, Sort sort); // NOTE: Pageable embeds a Sort }
  • 22.
  • 23.
    Explicit Queries public interfaceProductsRepository extends JpaRepository<Product, Long> { @Query(value = "select p from Product p order by p.rating desc", countQuery = "select count(p) from Product p") Page<Product> findTopRated(Pageable pageable); }
  • 24.
  • 25.
  • 26.
  • 27.
  • 28.
  • 30.
  • 31.
    Mongo DB -schema-less document DB databases mongo> show dbs; myDatabase 0.3046578 GB mongo> use myDatabase; collections mongo> show collections; rockCollection colleagueSean mongo> db.rockCollection.find().pretty(); // last call “prettifies” output documents mongo> db.rockCollection.find({name:"The Beatles"}).pretty(); {"_id" : ObjectId("50b7d870744e5ef5eee5224e"), "_class" : "xxx.music.domain.Band", "name" : "The Beatles", [...] }
  • 32.
    MongoDB: Queries asJSON documents db.inventory.find({ price:1.99, $or: [ { qty: { $lt: 20 } }, { sale: true } ] })
  • 33.
    GridFS - canI haz large objectz? • mongo> show collections; – fs.chunks – fs.files • CHUNKS – 256KB portion of a Mongo object (a.k.a. file), stored into collection “fs.chunks” • FILES – Metadata about the file stored into “fs.files”: filename, content type ... • Spring Data brings – GridFsTemplate – GridFsResource (wraps GridFSDBFile) 33
  • 35.
  • 36.
    Nodes NoSQL Spring HELPS_WITH standsFor: "Not Only Data how: "it roxx" SQL" IS_PART_OF Properties Relationship Spring
  • 37.
  • 38.
    Neo4J - CypherQuery Language start doctor=node:characters(character = 'Doctor') match (doctor)<-[:COMPANION_OF]-(companion) -[:APPEARED_IN]->(episode) return companion.character, count(episode) order by count(episode) desc limit 5
  • 39.
    Image credits • keys http://www.sxc.hu/photo/1381979 • spiderweb http://www.sxc.hu/photo/1309629 • columns http://www.sxc.hu/photo/511217 • documents http://www.sxc.hu/photo/913588 • umbrella http://www.sxc.hu/photo/1182110 • nail http://www.sxc.hu/photo/1101239 • relational http://www.sxc.hu/photo/541351 • callback http://www.sxc.hu/photo/1134440 • repositories http://www.sxc.hu/photo/1352633 • pagination http://www.sxc.hu/photo/830250 • magic http://www.sxc.hu/photo/829135 • cypher http://www.sxc.hu/photo/1118342 • mapping http://www.sxc.hu/photo/1147986 • grid http://www.sxc.hu/photo/1222068 • elephant http://www.sxc.hu/photo/1168187 • cross knot http://www.sxc.hu/photo/1396427 • rope knot http://www.sxc.hu/photo/1181983 • married http://www.sxc.hu/photo/937988 • shell http://www.sxc.hu/photo/866402 • diesel http://www.sxc.hu/photo/1076436 • car tuning http://www.sxc.hu/photo/5877 • rest on couch: If you haven’t, go watch Fight Club. NOW. 39