Object-Relational Mapping (ORM) And Hibernate
Agenda Introduction
to ORM Overview of Hibernate Why Hibernate Layered Architecture Configuration Mapping
Introduction To ORM
Object Persistence
Saving Object for future use Storage could be a file system, RDBMS etc Popular data storage systems are RDBMS Objects are not directly mapped to RDBMS tables
Traditional Solutions
JDBC/SQL Code embedded in classes More coding, container dependent Best practice would be to keep the persistence separate from classes
Introduction To ORM Contd..
New Solution – Object Relational Mapping
Persists Objects in a Relational Database Transparent solution; underlying tables are hidden from classes Support CRUD (Create, Read, Update and Delete) operations
ORM Solutions
Hibernate – Open Source iBatis SQL Maps – Open Source TopLink – Commercial JPA – Java EE 5 Solution
Overview of Hibernate Light-weight ORM solution (doesn’t require container) Object based model Transparent solutions Latest Version 3.x
Why Hibernate? Hibernate is built on top of JNDI, JDBC, JTA It uses XML based configuration files for mapping Supports many databases like Sybase, Oracle, MySQL etc. Easy migration from one vendor database to another Provides quite powerful object query language known as Hibernate Query Language (HQL)
Layered Architecture
Layered Architecture Contd..
Session Factory
Obtained from a Configuration instance. Main purpose is to provide Session instances Allowed to instantiate more than one SessionFactory Sophisticated implementation of the factory design pattern
Session
A single-threaded, short-lived object representing a conversation between the application and the persistent store. Wraps a JDBC connection. Factory for Transaction. Holds a mandatory (first-level) cache of persistent objects, used when navigating the object graph or looking up objects by identifier.
Layered Architecture Contd..
Persistent Objects and Collections
Short-lived, single threaded objects containing persistent state and business function. These might be ordinary JavaBeans/POJOs, the only special thing about them is that they are currently associated with (exactly one) Session. As soon as the Session is closed, they will be detached and free to use in any application layer (e.g. directly as data transfer objects to and from presentation).
Transient Objects and Collections
Instances of persistent classes that are not currently associated with a Session. They may have been instantiated by the application and not (yet) persisted or they may have been instantiated by a closed Session.
Layered Architecture Contd..
Transaction
Connection Provider
(Optional) A single-threaded, short-lived object used by the application to specify atomic units of work. Abstracts application from underlying JDBC, JTA or CORBA transaction. Multiple transactions per Session.
(Optional) A factory for (and pool of) JDBC connections. Abstracts application from underlying Datasource or DriverManager. Not exposed to application, but can be extended/implemented by the developer.
Transaction Factory
(Optional) A factory for Transaction instances. Not exposed to the application, but can be extended/implemented by the developer.
Configuration File:hibernate.cfg.xml
<session-factory> <property name="hibernate.connection.driver_class">org.hsqldb.jdbcDriver <property name="hibernate.connection.url">jdbc:hsqldb:hsql://localhost <property name="hibernate.connection.username">TOB <property name="hibernate.connection.password">TOB <property name="dialect">org.hibernate.dialect.HSQLDialect <property name="hibernate.connection.pool_size">10 <mapping resource=”Event.hbm.xml"/> <mapping resource=”Trust.hbm.xml”/>
Pojo’s (Plain Old Java Object) public class Trust { private int id; private String title; private Set<Event> events= new HashSet<Event>(); public Trust() { } public int getId() { return id; } private void setId( int id ) { this.id = id; } public String getTitle() { return title; } public void setTitle( String title ) { this.title = title; } Public set getEvents() { return events; } Public void setEvemts(set events) { this.events=events; }
}
Mapping Collection mapping Association mapping
Unidirectional one-to-many Unidirectional many-to-many Bidirectional one-to-many Bidirectional many-to-many
Component mapping
Collection Mapping
Collection properties must be declared as an interface type (Set, not HashSet) Hibernate provides built-in mapping for Set, Map, List and more May contain basic types, custom types and references to other Hibernate objects Collections are represented by a collection table in the database
Collection key: foreign key of owning object Collection element: object in the collection
Collection Mapping (Set) Contd.. Java Object
Collection declared as interface Type
Hibernate Mapping
Refers To Java property
public class Person { private int id; // other properties private Set<String> emails; // get and set methods }
<set name=”emails” table=”person_emails”>
Foreign key to owner
<element column=”email” type=”string”/>
Actual content of set
Collection Mapping (List) Contd..
Indexed collections
All ordered collection mappings need an index column in the collection table to persist the sequence Index of List is always of type Integer, index of Map can be of any type
Collection Mapping (List) Contd.. Java Object
List is an ordered type of collection
List mapped to table
Required mapping of index column
public class Person { private int id; // other properties private List<String> phnum; // get and set methods }
<list name=”phoneNumbers” table=”phone_numbe <list-index column=”sort_order” base=”0”/> <element column=”phone_number” type=”string
Collection Mapping (Bag & Array)
Bag
A
is an unordered collection, which can contain duplicated elements. There is not a “bag” concept in Java collections framework, so we just use a java.util.List to correspond to a . Eg: <element column="CHAPTER" type="string" length="100" />
Array
It corresponds to an array type in Java, not a java.util.List.
Eg: <array name="chapters" table="BOOK_CHAPTER"> <list-index column="CHAPTER_INDEX"/> <element column="CHAPTER" type="string" length="100" />
One-to-many (Unidirectional) Set of Persons
public class Event { private int id; private Set persons }
N 1
// id and other properties <set name=”persons” table=”events_persons”> // id properties
public class Person { private int id; // other properties }
Many-to-many (Unidirectional) Set of Persons
public class Event { private int id; private Set persons }
N N
public class Person { private int id; // other properties }
// id and other properties <set name=”persons” table=”events_persons”> <many-to-many column=”person_id” class=”model.Person”/> /> // id properties
One-to-Many (Bidirectional) Set of Persons
public class Event { private int id; private Set persons; }
N 1
// id and other properties <set name=”persons” table=”events_persons”> /> <many-to-one name=“Event" class=“model.Event" fetch="select" >
public class Person { private int id; private Event event; // other properties }
Many-to-many (Bidirectional) Set of Persons
public class Event { private int id; private Set persons }
N N
public class Person { private int id; private Set<Event> events // other properties }
// id and other properties <set name=”persons” table=”events_persons”> <many-to-many column=”person_id” class=”model.Person”/> /> <set name=”events” table=”events_persons” inverse=”true”> <many-to-many column=”event_id” class=”model.Event”/>
Hibernate Attributes
Lazy
Cascade
Save-or-update, delete, all, all-delete-orphan
Fetch
Proxy, true, false
Select, join
Inverse
True, false
Component mapping A component is an object saved as a value, not as a reference Saved directly – no need to declare interfaces or identifiers Required to define an empty constructor
Component mapping public class Address { private String street; private int postalCode; private String city; // no-arg constructor, get/set }
public class Person { private Address address; // get and set methods // other properties }
<property name=”street”/> <property name= postalCode /> <property name=”city”/>