SpringSource and MongoDBChris RichardsonAuthor of POJOs in ActionFounder of CloudFoundry.comChris.Richardson@SpringSource....
Presentation Goal  How SpringSource is   making it easier for     Java and Grails   developers to build  MongoDB applicati...
About Chris        •    Grew up in England and live in Oakland, CA        •    Over 25+ years of software development     ...
Agenda   Introduction to Spring   Spring Data and MongoDB   Introduction to Grails   Using Grails with MongoDB            ...
The Spring framework   Rapid evolution !    Spring 1.0 – March 2004 !    Spring 2.0 – October 2006 !    Spring 2.5 – Decem...
The Spring framework ecosystemFramework                         DescriptionSpring framework                  The foundatio...
Spring programming model                       Dependency Injection:                     resolves inter-component   Benefi...
Portable service abstractions  Portable service  abstractions  insulate developer         Business                        ...
Spring JDBC example@Repositoryclass ActorDaoImpl implements ActorDao {                                                    ...
Externalized database configuration@Configurationpublic class AppConfig {  private @Value("#{jdbcProperties.url}") String ...
Spring DataAccessException   Base class forexceptions thrown by                                    DataAccess             ...
Agenda   Introduction to the Spring framework   Spring Data and MongoDB   Introduction to Grails   Using Grails with Mongo...
Spring Data Project Goals   Bring classic Spring value propositions   to a wide range of NoSQL databases: !  Productivity ...
MongoDB API usage patterns   Create and store Mongo singleton   Externalized server details   Inserts/Updates  !  Map appl...
Spring Data - MongoDB   MongoTemplate   Generic repository implementation   Querydsl integration   Cross-store persistence...
MongoTemplateSimplifies data         MongoTemplate              POJO $ DBObjectaccess            databaseName             ...
Example entitypublic class Restaurant { private String id; private String name; private List<MenuItem> menuItems; public R...
Example data access code@Repositorypublic class RestaurantRepository { @Autowired private MongoTemplate mongoTemplate; pub...
Mongo document{    "_id" : ObjectId("4d977f55d3fe3119c904e026"),    "menuItems" : [         {                "name" : "Tan...
Spring MongoDB Example - Config@Configuration public class MongoDbExampleConfig { private @Value("#{mongoDbProperties.data...
Spring MongoDB Example Testpublic class MongoDbExampleTest { @Autowired private RestaurantRepository restaurantRepository;...
Update example@Repositorypublic class RestaurantRepository {  public void addMenuItem(String restaurantId,                ...
Callbacks – access driver API with  exception translation@Testpublic void testDbCallback() {                     Exception...
Generic Mongo Repositories   Generic Repositories support !  Basic CRUD methods !  Dynamic finders !  Pagination and sorti...
Example Mongo Generic Repositorypublic class Person {  private ObjectId id;  private String firstname;  private String las...
Example Mongo Repository config<bean><mongo:repositories base-package="net.chrisrichardson.mongodb.example.mongorepository...
Richer mapping                       Annotations define mapping:                                       @Document, @Id, @In...
Richer mapping configuration@Configurationpublic class MongoExampleConfig extends AbstractMongoConfiguration{ …    @Overri...
Support for the QueryDSL project Generated from                         Type-safe domain model class                     c...
Cross-store/polyglot persistence                                Person person = new Person(…);@Entitypublic class Person {...
Spring MongoDB – Future Ideas   MongoTemplate !  Support common map-reduce operations    from Mongo Cookbook !  GridFS int...
Agenda   Introduction to Spring   Spring Data and MongoDB   Introduction to Grails   Using Grails with MongoDB            ...
Grails   Open-source web application framework   Uses Groovy – dynamic programming language   for the JVM   Builds on matu...
GORM = Grails Object Relational Mapping   Uses convention over configuration  !  Defaults for which classes to persist  ! ...
Database access made easy                                                       customer class Customer {                 ...
Relationships don’t have to be difficult                                                customerclass Customer {          ...
When the defaults aren’t rightclass Customer {   static transients = ["networth"]    static mapping = {      id column: cu...
Agenda   Introduction to Spring   Spring Data and MongoDB   Introduction to Grails   Using Grails with MongoDB            ...
GORM for MongoDB   Extends GORM to support MongoDB   Announced Nov 2010   Currently 1.0M5   Builds on !  Spring Data for M...
GORM/MongoDB examplegrails uninstall-plugin hibernategrails install-plugin mongodbclass Customer {   String name          ...
GORM/MongoDB example> db.customer.find(){ "_id" : NumberLong(24), "address" : { "city" : "Oakland", "state" : "CA",       ...
Cloud Foundry supports Mongo    MongoDB is one of the provided services" Deploy your MongoDB applications inseconds       ...
Summary  Polyglot persistence is here to stay  Spring Data is here to help you  GORM let’s you use the familiar and  power...
Next steps                    Checkout Spring Data                    Consider contributing                    Deploy on C...
Upcoming SlideShare
Loading in...5
×

MongoDB for Java Devs with Spring Data - MongoPhilly 2011

16,564

Published on

0 Comments
22 Likes
Statistics
Notes
  • Be the first to comment

No Downloads
Views
Total Views
16,564
On Slideshare
0
From Embeds
0
Number of Embeds
0
Actions
Shares
0
Downloads
0
Comments
0
Likes
22
Embeds 0
No embeds

No notes for slide

MongoDB for Java Devs with Spring Data - MongoPhilly 2011

  1. 1. SpringSource and MongoDBChris RichardsonAuthor of POJOs in ActionFounder of CloudFoundry.comChris.Richardson@SpringSource.Com@crichardson
  2. 2. Presentation Goal How SpringSource is making it easier for Java and Grails developers to build MongoDB applications Slide 2
  3. 3. About Chris •  Grew up in England and live in Oakland, CA •  Over 25+ years of software development experience including 14 years of Java •  Speaker at JavaOne, SpringOne, NFJS, JavaPolis, Spring Experience, etc. •  Organize the Oakland JUG and the Groovy Grails meetup http://www.theregister.co.uk/2009/08/19/springsource_cloud_foundry/ Slide 3
  4. 4. Agenda   Introduction to Spring   Spring Data and MongoDB   Introduction to Grails   Using Grails with MongoDB Slide 4
  5. 5. The Spring framework   Rapid evolution !  Spring 1.0 – March 2004 !  Spring 2.0 – October 2006 !  Spring 2.5 – December 2007 !  Spring 3.0 – December 2009 !  … !  Complete backward compatibility   De facto standard programming model for enterprise Java   Two million+ developers Slide 5
  6. 6. The Spring framework ecosystemFramework DescriptionSpring framework The foundationSpring.NET .NET port of the Spring frameworkSpring Security (a.k.a. Acegi) Extensible framework providing authentication, authorization and instance-level securitySpring Web Flow An excellent framework for building multi-page flowsSpring Web Services Contract-first, document–centric SOAP web servicesSpring Dynamic Modules for OSGI Deploy Spring applications on OSGISpring Batch Powerful batch processing frameworkSpring Integration Implements enterprise integration patternsSpring BlazeDS integration Support for Adobe BlazeDSSpring AMQP AMQP messaging, i.e. RabbitMQSpring Gemfire Simplify Gemfire application development… Slide 6
  7. 7. Spring programming model Dependency Injection: resolves inter-component Benefits: dependencies, • Improved developer metadata-driven productivity • Higher quality code • Portability across application servers POJO Aspect-Oriented Programming:Portable Service modularAbstractions: implementation ofTransactions, data cross cuttingaccess, … concerns Slide 7
  8. 8. Portable service abstractions  Portable service abstractions insulate developer Business Logic from low-level programming Infrastructure code  Less code Spring  Simpler code Transactions Security Data access  Increased … productivity  Portable code Runtime Environment Slide 8
  9. 9. Spring JDBC example@Repositoryclass ActorDaoImpl implements ActorDao { SimpleJdbcTemplate hides@Autowired the low-level, messyprivate SimpleJdbcTemplate simpleJdbcTemplate; details of using JDBCpublic Actor findActor(String specialty, int age) { String sql = "select id, first_name, last_name from T_ACTOR" + " where specialty = ? and age = ?"; RowMapper<Actor> mapper = new RowMapper<Actor>() { public Actor mapRow(ResultSet rs, int rowNum) throws SQLException { Actor actor = new Actor(); actor.setId(rs.getLong("id")); actor.setFirstName(rs.getString("first_name")); actor.setLastName(rs.getString("last_name")); return actor; } }; return simpleJdbcTemplate.queryForObject(sql, mapper, specialty, age);} Slide 9
  10. 10. Externalized database configuration@Configurationpublic class AppConfig { private @Value("#{jdbcProperties.url}") String jdbcUrl; private @Value("#{jdbcProperties.username}") String username; private @Value("#{jdbcProperties.password}") String password; @Bean public SimpleJdbcTemplate jdbcTemplate() { return new SimpleJdbcTemplate (dataSource()); } @Bean public DataSource dataSource() { return new DriverManagerDataSource(jdbcUrl, username, password); }} Reads DB configuration<context:component-scan base-package="..."/> from file<util:properties id="jdbcProperties" location="…/jdbc.properties"/> Slide 10
  11. 11. Spring DataAccessException  Base class forexceptions thrown by DataAccess ExceptionDAOs  Consistent exception Concurrency Failure Exception ...handling acrossHibernate, JPA, JDBC, Optimistic LockingFailureetc. Exception Pessimistic LockingFailure Exception  Unchecked exception  Extensible exception CannotSerializemapping: CannotAcquire LockException Transaction ExceptionSqlExceptionTranslator 11
  12. 12. Agenda   Introduction to the Spring framework   Spring Data and MongoDB   Introduction to Grails   Using Grails with MongoDB Slide 12
  13. 13. Spring Data Project Goals   Bring classic Spring value propositions to a wide range of NoSQL databases: !  Productivity !  Programming model consistency: E.g. <NoSQL>Template classes !  “Portability”   Many entry points to use !  Auto-generated repository implementations !  Opinionated APIs (Think JdbcTemplate) !  Object Mapping (Java and GORM) !  Cross Store Persistence Programming model !  Productivity support in Roo and Grails Slide 13
  14. 14. MongoDB API usage patterns   Create and store Mongo singleton   Externalized server details   Inserts/Updates !  Map application POJO " DBObject !  mongo.getDatabase(…).getCollection(…) !  Partial document updates   Queries !  mongo.getDatabase(…).getCollection(…) !  Iterate through Cursor !  Map DBObject " application POJO#  Higher-level than JDBC but still repetitive, … Slide 14
  15. 15. Spring Data - MongoDB   MongoTemplate   Generic repository implementation   Querydsl integration   Cross-store persistence Slide 15
  16. 16. MongoTemplateSimplifies data MongoTemplate POJO $ DBObjectaccess databaseName mappingTranslates userId Passwordexceptions defaultCollectionName writeConcern writeResultChecking <<interface>> save() MongoConvertor insert() write(Object, DBObject) remove() read(Class, DBObject) updateFirst() findOne() find() … SimpleMongo uses Converter Mongo MongoMapping (Java Driver class) Converter Slide 16
  17. 17. Example entitypublic class Restaurant { private String id; private String name; private List<MenuItem> menuItems; public Restaurant() { } public class MenuItem { private String name; public Restaurant(String name) { private double price; this.name = name; … public MenuItem() { } }public String getName() { return name; } public MenuItem(String name, double price) { this.name = name; public void setName(String name) { this.price = price; this.name = name; } } …getters and setters… …getters and setters… Slide 17
  18. 18. Example data access code@Repositorypublic class RestaurantRepository { @Autowired private MongoTemplate mongoTemplate; public static final String RESTAURANTS_COLLECTION = "restaurants2"; public void add(Restaurant restaurant) { mongoTemplate.save(RESTAURANTS_COLLECTION, restaurant); }public List<Restaurant> findRestaurantsByName(String restaurantName) { return mongoTemplate.find(RESTAURANTS_COLLECTION, new Query(where("name").is(restaurantName)), Restaurant.class); } Slide 18
  19. 19. Mongo document{ "_id" : ObjectId("4d977f55d3fe3119c904e026"), "menuItems" : [ { "name" : "Tandoori Portobello Mushrooms", "price" : 5.5 }, { "name" : "Duck Curry Kerala", "price" : 15 } ], "name" : "Ajanta"} Slide 19
  20. 20. Spring MongoDB Example - Config@Configuration public class MongoDbExampleConfig { private @Value("#{mongoDbProperties.databaseName}") String mongoDbDatabase; private @Value("#{mongoDbProperties.host}") String mongoDbHost;@Bean public Mongo mongo() throws Exception { Singleton return new Mongo(mongoDbHost);} @Bean public MongoTemplate mongoTemplate(Mongo mongo) { return new MongoTemplate(mongo, mongoDbDatabase); }… <beans> <context:annotation-config/> External Config <context:component-scan base-package="net.chrisrichardson.mongodb.example"/>mongodb.properties: <util:properties id="mongoDbProperties" location="mongodb.properties"/>databaseName=demo1 </beans>host=192.168.253.150 Slide 20
  21. 21. Spring MongoDB Example Testpublic class MongoDbExampleTest { @Autowired private RestaurantRepository restaurantRepository; @Test public void test() { Restaurant ajanta = makeAjantaRestaurant(); restaurantRepository.add(ajanta); List<Restaurant> results = restaurantRepository.findRestaurantsByName("Ajanta"); assertRestaurantFound(ajanta, results); } private Restaurant makeAjantaRestaurant() { Restaurant ajanta = new Restaurant("Ajanta"); ajanta.add(new MenuItem("Tandoori Portobello Mushrooms", 5.50)); ajanta.add(new MenuItem("Duck Curry Kerala", 15.00)); return ajanta; }… Slide 21
  22. 22. Update example@Repositorypublic class RestaurantRepository { public void addMenuItem(String restaurantId, MenuItem newMenuItem) { DBObject dbo = new BasicDBObject(); mongoTemplate.getConverter().write(newMenuItem, dbo); mongoTemplate.updateFirst(RESTAURANTS_COLLECTION, new Query(where("_id").is(new ObjectId(restaurantId))), new Update().push("menuItems", dbo));} Atomic, in-place update of document Slide 22
  23. 23. Callbacks – access driver API with exception translation@Testpublic void testDbCallback() { Exceptions are Restaurant ajanta = makeAjantaRestaurant(); translated restaurantRepository.add(ajanta); assertCollectionExists("restaurants2");}private Void assertCollectionExists(final String collectionName) { return mongoTemplate.execute(new DbCallback<Void>(){ @Override public Void doInDB(DB db) { Set<String> collectionNames = db.getCollectionNames(); Assert.assertTrue("Missing from " + collectionNames, collectionNames.contains(collectionName)); return null; }});} Slide 23
  24. 24. Generic Mongo Repositories   Generic Repositories support !  Basic CRUD methods !  Dynamic finders !  Pagination and sorting   You define interface that extends Repository interface   Spring Data generates Mongo-specific implementation at runtime Slide 24
  25. 25. Example Mongo Generic Repositorypublic class Person { private ObjectId id; private String firstname; private String lastname;… getters and setters}interface PersonRepository extends MongoRepository<Person, ObjectId> { List<Person> findByLastname(String lastName);}Person p = new Person("John", "Doe");personRepository.save(p);Person p2 = personRepository.findOne(p.getId());List<Person> johnDoes = personRepository.findByLastname("Doe");assertEquals(1, johnDoes.size()); Slide 25
  26. 26. Example Mongo Repository config<bean><mongo:repositories base-package="net.chrisrichardson.mongodb.example.mongorepository" mongo-template-ref="mongoTemplate" /></beans> Scans classpath looking for subtypes of MongoRepository in the base package Slide 26
  27. 27. Richer mapping Annotations define mapping: @Document, @Id, @Indexed, @PersistanceConstructor,@Document @CompoundIndex, @DBRef,public class Person { @GeoSpatialIndexed, @Value @Id Map fields instead of properties " private ObjectId id; no getters or setters required private String firstname; Non-default constructor @Indexed private String lastname; Index generation @PersistenceConstructor public Person(String firstname, String lastname) { this.firstname = firstname; this.lastname = lastname; }….} Slide 27
  28. 28. Richer mapping configuration@Configurationpublic class MongoExampleConfig extends AbstractMongoConfiguration{ … @Override public MongoTemplate mongoTemplate() throws Exception { return new MongoTemplate(mongo(), mongoDbDatabase, null, mappingMongoConverter()); }@Overridepublic String getMappingBasePackage() { return Person.class.getPackage().getName();}} Slide 28
  29. 29. Support for the QueryDSL project Generated from Type-safe domain model class composable queriesQPerson person = QPerson.person;Predicate predicate = person.homeAddress.street1.eq("1 High Street") .and(person.firstname.eq("John"))List<Person> people = personRepository.findAll(predicate);assertEquals(1, people.size());assertPersonEquals(p, people.get(0)); Slide 29
  30. 30. Cross-store/polyglot persistence Person person = new Person(…);@Entitypublic class Person { entityManager.persist(person); // In Database @Id private Long id; Person p2 = entityManager.find(…) private String firstname; private String lastname;// In MongoDB@RelatedDocument private Address address; { "_id" : ObjectId(”….."), "_entity_id" : NumberLong(1), "_entity_class" : "net.. Person", "_entity_field_name" : "address", "zip" : "94611", "street1" : "1 High Street", …} Slide 30
  31. 31. Spring MongoDB – Future Ideas   MongoTemplate !  Support common map-reduce operations from Mongo Cookbook !  GridFS integration   Tighter integration with Spring MVC for activity monitoring !  See current example code on github Slide 31
  32. 32. Agenda   Introduction to Spring   Spring Data and MongoDB   Introduction to Grails   Using Grails with MongoDB Slide 32
  33. 33. Grails   Open-source web application framework   Uses Groovy – dynamic programming language for the JVM   Builds on mature frameworks such as Spring Slide 33
  34. 34. GORM = Grails Object Relational Mapping   Uses convention over configuration !  Defaults for which classes to persist !  Defaults for their O/R mapping   Leverages the meta-object protocol !  Adds persistence methods and properties to domain classes !  No equivalent of Hibernate Session !  Avoids the need for dependency injection !  Eliminates many DAO cookie-cutter methods Slide 34
  35. 35. Database access made easy customer class Customer { <<table>> String name id <<pk>> } version name Customer c = new Customer("John Doe") if (!c.save()) fail "validation failed: ${c.errors}" GORM adds Methods and Customer c2 = Customer.get(c.id) properties to class at runtime c2.delete() assertNull Customer.get(c.id) def customers = Customer.findAllByName(“Fred”) Slide 35
  36. 36. Relationships don’t have to be difficult customerclass Customer { <<table>> String name id <<pk>> static hasMany = [ accounts : Account] version} nameclass Account { account static belongsTo = [customer: Customer] <<table>> double balance id <<pk>>} version customer <<fk>> Customer c = <…> balance Account a = new Account(…) c.addToAccounts(a) assertSame c, a.customer assertTrue c.accounts.contains(a) Slide 36
  37. 37. When the defaults aren’t rightclass Customer { static transients = ["networth"] static mapping = { id column: customer_id crc_customer <<table>> table crc_customer columns { customer_id <<pk>> version name column: customer_name customer_name } } def getNetworth() { …} …} Slide 37
  38. 38. Agenda   Introduction to Spring   Spring Data and MongoDB   Introduction to Grails   Using Grails with MongoDB Slide 38
  39. 39. GORM for MongoDB   Extends GORM to support MongoDB   Announced Nov 2010   Currently 1.0M5   Builds on !  Spring Data for MongoDB !  Spring Data Mapping Slide 39
  40. 40. GORM/MongoDB examplegrails uninstall-plugin hibernategrails install-plugin mongodbclass Customer { String name Unchanged Address address static hasMany = [ accounts : Account] static embedded = [address]} class Address { String streetclass Account { String city static belongsTo = [customer: Customer] String state double balance String zip} }DataSource.groovymongo { host = "localhost"} Slide 40
  41. 41. GORM/MongoDB example> db.customer.find(){ "_id" : NumberLong(24), "address" : { "city" : "Oakland", "state" : "CA", "street" : "1 High Street", "zip" : "94619" }, "name" : "John Doe" }{ "_id" : NumberLong(25), "address" : { "city" : "Oakland", "state" : "CA", "street" : "101 Broadway", "zip" : "94619" }, "name" : "Mary Jane" }> db.account.find(){ "_id" : NumberLong(1), "balance" : 60, "customer" : NumberLong(24), "name" : "Checking" }{ "_id" : NumberLong(2), "balance" : 100, "customer" : NumberLong(24), "name" : "Savings" }{ "_id" : NumberLong(3), "balance" : 0, "customer" : NumberLong(25), "name" : "Checking" }   Domain class $ Collection   Property $ Attribute   Relationship $ "FK attribute" Slide 41
  42. 42. Cloud Foundry supports Mongo   MongoDB is one of the provided services" Deploy your MongoDB applications inseconds Slide 42
  43. 43. Summary  Polyglot persistence is here to stay  Spring Data is here to help you  GORM let’s you use the familiar and powerful GORM API with MongoDB  Deploy your Mongo application on CloudFoundry.com  More info at !  http://www.springframework.org/spring-data !  http://www.cloudfoundry.com/ Slide 43
  44. 44. Next steps Checkout Spring Data Consider contributing Deploy on CloudFoundry.com My contact information chris.richardson@springsource.com Twitter: @crichardson Slide 44

×