Spring Data NHJUG April 2012
Upcoming SlideShare
Loading in...5
×
 

Spring Data NHJUG April 2012

on

  • 2,043 views

 

Statistics

Views

Total Views
2,043
Views on SlideShare
2,042
Embed Views
1

Actions

Likes
1
Downloads
33
Comments
0

1 Embed 1

https://twitter.com 1

Accessibility

Categories

Upload Details

Uploaded via as Adobe PDF

Usage Rights

© All Rights Reserved

Report content

Flagged as inappropriate Flag as inappropriate
Flag as inappropriate

Select your reason for flagging this presentation as inappropriate.

Cancel
  • Full Name Full Name Comment goes here.
    Are you sure you want to
    Your message goes here
    Processing…
Post Comment
Edit your comment

Spring Data NHJUG April 2012 Spring Data NHJUG April 2012 Presentation Transcript

  • Spring Data Thomas Risberg VMware trisberg@vmware.comTuesday, April 17, 12 1
  • •expert in NO SQL • committer on Spring Framework • currently works for VMware’s Cloud • former Oracle DBA Foundry team on framework integration • former Java J2EE developer • member of Spring Data team email: trisberg@vmware.com twitter: @trisbergTuesday, April 17, 12 2
  • Tuesday, April 17, 12 3
  • New demands on data access ... • massive amounts of data • social networking features • structured and • inexpensive horizontal scaling unstructured data • deploying apps in the cloud • real-time analysis • ... image courtesy of BitcurrentTuesday, April 17, 12 4
  • New types of data stores ... Column/ • Redis • Cassandra • Riak • HBase • MongoDB • CouchDB • Neo4j HadoopTuesday, April 17, 12 5
  • Spring Framework built-in data access support • Transaction abstractions, Data access exceptions • JDBC - JdbcTemplate • ORM - Hibernate, JPA support • OXM - Object to XML mapping • Cache support (Spring 3.1)Tuesday, April 17, 12 6
  • Spring Data • Bring classic Spring benefits to all databases ✓ Productivity ✓ Programming model consistency • Conventions based generic repository support • Mapping between Java domain objects and data store • Support for a wide range of new databasesTuesday, April 17, 12 7
  • Spring Data sub-projects • JPA Repository • JDBC Extensions • Redis (Key Value) • MongoDB (Document) • Neo4j (Graph) • Gemfire (Data Grid) • Apache Hadoop (Big Data) • Riak (Key Value - in development) • Cassandra (Column Store - planned)Tuesday, April 17, 12 8
  • Spring Data Building Blocks • Low level data access APIs ✓ MongoTemplate, RedisTemplate ... • Object Mapping (Java to Datastore) • Generic Repository support • Cross Store Persistence Programming modelTuesday, April 17, 12 9
  • Finding Spring Data • GitHub: https://github.com/SpringSource • Web page: http://www.springsource.org/spring-data • Forum: http://forum.springsource.org/forumdisplay.php?f=80Tuesday, April 17, 12 10
  • Three databases for today’s talk • Relational database • Document database • Graph databaseTuesday, April 17, 12 11
  • Three persistence strategies for today’s talk • Conventions based persistence -- Repositories • Lower-level Template approach • Cross-store persistence using JPA and a non-relational databaseTuesday, April 17, 12 12
  • Repository http://www.sxc.hu/photo/1020163Tuesday, April 17, 12 13
  • Repository Mediates between the domain and data mapping layers using a collection-like interface for accessing domain objects. http://martinfowler.com/eaaCatalog/repository.html http://msdn.microsoft.com/en-us/library/ff649690.aspxTuesday, April 17, 12 14
  • Spring Data Repository • Generic repository implementation • Basic CRUD (create, read, update and delete) methods • Generating code for dynamic find methods defined in repository interface like findByName, findByAgeBetween etc. • Pagination and sorting support • Currently JPA, Mongo and Neo4j implementationsTuesday, April 17, 12 15
  • Repository<T, ID extends Serializable> CrudRepository<T, ID extends Serializable> PagingAndSortingRepository<T, ID extends Serializable>Tuesday, April 17, 12 16
  • Query MethodsTuesday, April 17, 12 17
  • <persistence> <?xml version="1.0" encoding="UTF-8"?> <persistence version="1.0" xmlns="http://java.sun.com/xml/ns/persistence" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/persistence http://java.sun.com/xml/ns/persistence/persistence_1_0.xsd"> <persistence-unit name="test"> <properties> <property name="hibernate.dialect" value="org.hibernate.dialect.MySQL5InnoDBDialect"/> <property name="hibernate.hbm2ddl.auto" value="update"/> <property name="hibernate.ejb.naming_strategy" value="org.hibernate.cfg.ImprovedNamingStrategy"/> </properties> </persistence-unit> </persistence>Tuesday, April 17, 12 18
  • <configuration> <jpa:repositories base-package="org.springframework.data.demo.repository" /> <tx:annotation-driven transaction-manager="transactionManager"/> <context:component-scan base-package="org.springframework.data.demo"> <context:exclude-filter expression="org.springframework.stereotype.Controller" type="annotation"/> </context:component-scan> <bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager"> <property name="entityManagerFactory" ref="entityManagerFactory" /> </bean> <bean id="entityManagerFactory" class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean"> <property name="dataSource" ref="dataSource" /> <property name="persistenceUnitName" value="test"/> <property name="jpaVendorAdapter"> <bean class="org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter"> <property name="generateDdl" value="true" /> </bean> </property> </bean>Tuesday, April 17, 12 19
  • r Fo lt ui B <beans profile="default"> <bean class="org.apache.commons.dbcp.BasicDataSource" destroy-method="close" id="dataSource"> <property name="driverClassName" value="com.mysql.jdbc.Driver"/> <property name="url" value="jdbc:mysql://localhost/test"/> <property name="username" value="root"/> <property name="password" value=""/> <property name="testOnBorrow" value="true"/> </bean> </beans> <beans profile="cloud"> <cloud:data-source id="dataSource"/> </beans>Tuesday, April 17, 12 20
  • App using JPA Repository CODE https://github.com/trisberg/jpa-bookshelf-repositoryTuesday, April 17, 12 21
  • { "title" : "Spring Data REST in Action", "price" : 22.55, "_links" : [ { "rel" : "author", "href" : "http://localhost:8080/data/author" }, { "rel" : "self", "href" : "http://localhost:8080/data/author/2" } ], "categories" : [ "Spring", "Java" ], "published" : "2012-04-24" } { "_links" : [ { "rel" : "Book", { "href" : "http://localhost:8080/data/author/2/books/1234567890" "name" : "Jon Brisbin", }] "_links" : [ { } "rel" : "books", "href" : "http://localhost:8080/data/author/2/books" }, { "rel" : "self", "href" : "http://localhost:8080/data/author/2" }] } https://github.com/SpringSource/spring-data-restTuesday, April 17, 12 22
  • Tuesday, April 17, 12 23
  • Application Document Oriented High { author: “steve”, date: new Date(), Performance text: “About MongoDB...”, tags: [“tech”, “database”]} Horizontally ScalableTuesday, April 17, 12 24
  • Documents > p = {author: “roger”, date: new Date(), text: “about mongoDB...”, tags: [“tech”, “databases”]} > db.posts.save(p)Tuesday, April 17, 12 25
  • Querying > db.posts.find() > { _id : ObjectId("4c4ba5c0672c685e5e8aabf3"), author : "roger", date : "Sat Jul 24 2010 19:47:11", text : "About MongoDB...", tags : [ "tech", "databases" ] }Tuesday, April 17, 12 26
  • Secondary Indexes // 1 means ascending, -1 means descending > db.posts.ensureIndex({author: 1}) > db.posts.find({author: roger}) > { _id : ObjectId("4c4ba5c0672c685e5e8aabf3"), author : "roger", ... }Tuesday, April 17, 12 27
  • Conditional Query Operators $all, $exists, $mod, $ne, $in, $nin, $nor, $or, $size, $type, $lt, $lte, $gt, $gte // find posts with any tags > db.posts.find( {tags: {$exists: true }} ) // find posts matching a regular expression > db.posts.find( {author: /^rog*/i } ) // count posts by author > db.posts.find( {author: ‘roger’} ).count()Tuesday, April 17, 12 28
  • Atomic Updates $set, $unset, $inc, $push, $pushAll, $pull, $pullAll, $bit > comment = { author: “fred”, date: new Date(), text: “Best Movie Ever”} > db.posts.update( { _id: “...” }, $push: {comments: comment} );Tuesday, April 17, 12 29
  • Nested Documents { _id : ObjectId("4c4ba5c0672c685e5e8aabf3"), author : "roger", date : "Sat Apr 24 2011 19:47:11", text : "About MongoDB...", tags : [ "tech", "databases" ], comments : [ { author : "Fred", date : "Sat Apr 25 2010 20:51:03 GMT-0700", text : "Best Post Ever!" } ] }Tuesday, April 17, 12 30
  • Advanced indexing // Index nested documents > db.posts.ensureIndex( “comments.author”: 1) > db.posts.find({‘comments.author’:’Fred’}) // Index on tags (multi-key index) > db.posts.ensureIndex( tags: 1) > db.posts.find( { tags: ‘tech’ } ) // geospatial index > db.posts.ensureIndex( “author.location”: “2d” ) > db.posts.find( “author.location”: { $near : [22,42] } )Tuesday, April 17, 12 31
  • Rich Documents { _id : ObjectId("4c4ba5c0672c685e5e8aabf3"), line_items : [ { sku: ‘tt-123’, name: ‘Coltrane: Impressions’ }, { sku: ‘tt-457’, name: ‘Davis: Kind of Blue’ } ], address : { name: ‘Banker’, street: ‘111 Main’, zip: 10010 }, payment: { cc: 4567, exp: Date(2011, 7, 7) }, subtotal: 2355 }Tuesday, April 17, 12 32
  • Getting started with $ wget http://fastdl.mongodb.org/osx/mongodb-osx-x86_64-2.0.4.tgz $ tar xvzf mongodb-osx-x86_64-2.0.4.tgz $ cd mongodb-osx-x86_64-2.0.4 $ ./bin/mongod --dbpath /Users/trisberg/Data/mongodb/ Sun Apr 15 11:33:11 [initandlisten] MongoDB starting : pid=34692 port=27017 dbpath=/Users/trisberg/Data/ mongodb/ 64-bit host=Montserrat.local Sun Apr 15 11:33:11 [initandlisten] db version v2.0.4, pdfile version 4.5 Sun Apr 15 11:33:11 [initandlisten] git version: 329f3c47fe8136c03392c8f0e548506cb21f8ebf Sun Apr 15 11:33:11 [initandlisten] build info: Darwin erh2.10gen.cc 9.8.0 Darwin Kernel Version 9.8.0: Wed Jul 15 16:55:01 PDT 2009; root:xnu-1228.15.4~1/RELEASE_I386 i386 BOOST_LIB_VERSION=1_40 Sun Apr 15 11:33:11 [initandlisten] options: { dbpath: "/Users/trisberg/Data/mongodb/" } Sun Apr 15 11:33:11 [initandlisten] journal dir=/Users/trisberg/Data/mongodb/journal Sun Apr 15 11:33:11 [initandlisten] recover : no journal files present, no recovery needed Sun Apr 15 11:33:12 [websvr] admin web console waiting for connections on port 28017 Sun Apr 15 11:33:12 [initandlisten] waiting for connections on port 27017Tuesday, April 17, 12 33
  • & $ vmc create-service mongodb mongo-books $ vmc tunnel mongo-books mongo Password: ***** Binding Service [mongo-books]: OK Stopping Application: OK Staging Application: OK Starting Application: OK Getting tunnel connection info: OK Service connection info: username : 97da4cc2-8919-42f9-8bdb-11f0e565c2b6 password : 61b04646-4f9f-4804-8360-20662c2a2c95 name : db Starting tunnel to mongo-books on port 10000. Launching mongo --host localhost --port 10000 -u 97da4cc2-8919-42f9-8bdb-11f0e565c2b6 -p 61b04646-4f9f-4804-8360-20662c2a2c95 db MongoDB shell version: 2.0.1 connecting to: localhost:10000/db > show collections author book system.indexes system.users > db.author.find() { "_id" : ObjectId("4f8af65d942bb7cb40b29764"), "_class" : "org.springframework.data.demo.domain.Author", "name" : "Craig Walls" } { "_id" : ObjectId("4f8af65d942bb7cb40b29765"), "_class" : "org.springframework.data.demo.domain.Author", "name" : "Kristina Chodorow" } ...Tuesday, April 17, 12 34
  • Spring Data MongoDB ✓ MongoTemplate • MongoConverter interface for mapping Mongo documents • MappingMongoConverter for POJO mapping support, leveraging Spring TypeConverters • Annotation based mapping (@Document, @Id, @DbRef) • Connection affinity callbacks • Exception translation • Support for GridFS and Map Reduce ✓ MongoRepository • Similar support as JPA RepositoriesTuesday, April 17, 12 35
  • <configuration> <bean id="mongoTemplate" class="org.springframework.data.mongodb.core.MongoTemplate"> <constructor-arg name="mongoDbFactory" ref="mongoDbFactory"/> </bean> <context:component-scan base-package="org.springframework.data.demo"> <context:exclude-filter expression="org.springframework.stereotype.Controller" type="annotation"/> </context:component-scan>Tuesday, April 17, 12 36
  • r Fo lt ui B <beans profile="default"> <mongo:db-factory host="localhost" port="27017" dbname="db"/> </beans> <beans profile="cloud"> <cloud:mongo-db-factory id="mongoDbFactory" write-concern="NORMAL"/> </beans>Tuesday, April 17, 12 37
  • Document store using MongoTemplate LIVE CODE https://github.com/trisberg/mongo-bookshelf-templateTuesday, April 17, 12 38
  • • DB is a collection of graph nodes, relationships • Nodes and relationships have properties • Querying is done via a traversal API • Indexes on node/relationship properties • Written in Java, can be embedded • Transactional (ACID) • Master-Slave replication • Standalone using REST APITuesday, April 17, 12 39
  • Neo4j Data ModelTuesday, April 17, 12 40
  • Features • Support for property graphs (nodes connected via relationships, each with arbitrary properties) • Transparent mapping of annotated POJO entities (using AspectJ • Neo4jTemplate with convenient API, exception translation and optional transaction management • Supports the Cypher and Gremlin query languages • Dynamic type projections (duck typing) • Spring Data Repositories Support • Cross-store support for partial JPA – Graph EntitiesTuesday, April 17, 12 41
  • Cross-store • JPA data and “NOSQL” data can share a data model • Separate the persistence provider by using annotations – could be the entire Entity – or, some of the fields of an Entity • We call this cross-store persistence – One transaction manager to coordinate the “NOSQL” store with the JPA relational database – AspectJ support to manage the “NOSQL” entities and fields • holds on to changed values in “change sets” until the transaction commits for non-transactional data storesTuesday, April 17, 12 42
  • A cross-store scenario ... You have a traditional web app using JPA to persist data to a relational databaseTuesday, April 17, 12 43
  • JPA Data Model Restaurant UserAccount @Entity @Entity public class Restaurant { @Table(name = "user_account") @Id @GeneratedValue public class UserAccount { private Long id; @Id @GeneratedValue private String name; private Long id; private String city; private String userName; private String state; private String firstName; private String zipCode; private String lastName; @Temporal(TemporalType.TIMESTAMP) private Date birthDate; @ManyToMany(cascade = CascadeType.ALL) private Set<Restaurant> favorites;Tuesday, April 17, 12 44
  • Cross-store Data Model Restaurant UserAccount @Entity @Entity @NodeEntity(partial = true) @Table(name = "user_account") public class Restaurant { @NodeEntity(partial = true) @Id @GeneratedValue public class UserAccount { private Long id; @Id @GeneratedValue private String name; private Long id; private String city; private String userName; private String state; private String firstName; private String zipCode; private String lastName; @Temporal(TemporalType.TIMESTAMP) private Date birthDate; @ManyToMany(cascade = CascadeType.ALL) Recommendation private Set<Restaurant> favorites; @RelationshipEntity @GraphProperty public class Recommendation { String nickname; @StartNode @RelatedTo(type = "friends", private UserAccount user; elementClass = UserAccount.class) @EndNode Set<UserAccount> friends; private Restaurant restaurant; @RelatedToVia(type = "recommends", private int stars; elementClass = Recommendation.class) private String comment; Iterable<Recommendation> recommendations;Tuesday, April 17, 12 45
  • Cross-store persistence with JPA/Neo4j DEMO https://github.com/SpringSource/spring-data-neo4j/tree/ 2.0.1.RELEASE/spring-data-neo4j-examples/myrestaurants-socialTuesday, April 17, 12 46
  • Questions? http://www.sxc.hu/photo/860327Tuesday, April 17, 12 47