Enterprise Java Development@TOPIC@

Java Persistence API

Entities and EntityManager

Revision: v2013-08-19

Built on: 2014-03-06 23:58 EST

Abstract

This presentation provides and introduction to JPA and coverage of the methods of the EntityManager.


Purpose
1. Goals
2. Objectives
1. JPA Overview
1.1. Background
1.2. EntityManager
1.3. Entity
1.4. JPA Example
1.5. Entity States
1.5.1. Managed
1.5.2. Detached
1.6. Persistence Context
1.7. Persistence Unit
1.8. Example Layout
1.9. Persistence.xml
1.9.1. Application Example
1.9.2. Server Example
1.9.3. Optional hibernate.properties
1.9.4. Sample orm.xml
1.9.5. persistrence.xml Elements
1.9.6. Entity Discovery
1.10. Basic Steps
1.11. Entity Manager Methods
1.11.1. Basic CRUD Operations
1.11.2. Membership Operations
1.11.3. State Synchronization Operations
1.11.4. Locking Operations
1.11.5. Query Operations
1.11.6. Other Operations
2. Entity Manager CRUD Methods
2.1. persist()
2.2. find()
2.3. getReference()
2.4. merge()
2.5. remove()
3. Entity Manager Membership Methods
3.1. contains()
3.2. clear()
3.3. detach()
4. Entity Manager State Synchronization Methods
4.1. flush()
4.2. FlushMode
4.3. refresh()
5. Entity Manager Locking Methods
5.1. Primary Lock Types
5.2. LockModeType
5.3. lock()
5.4. find(lock)
5.5. refresh(lock)
5.6. getLockMode()
6. Entity Manager Query Methods
6.1. JPA Queries
6.2. Native Queries
6.3. Criteria Queries
7. Other Entity Manager Methods
7.1. isOpen()
7.2. close()
7.3. getTransaction()
7.4. joinTransaction()
7.5. unwrap()
7.6. getDelegate()
7.7. getMetaModel()
7.8. getEntityManagerFactory()
7.9. setProperties()/getProperties()
8. JPA Maven Environment
8.1. JPA Maven Dependencies
8.1.1. JPA API classes
8.1.2. JPA Provider classes
8.1.3. Database
8.2. Supplying Runtime Properties
8.2.1. Turn on Resource Filtering in pom.xml
8.2.2. Use ${variable} References in Resource Files
8.2.3. Define Property Values in Parent pom.xml
8.2.4. Run with Filtered Values


<?xml version="1.0" encoding="UTF-8"?>
<persistence 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_2_0.xsd" 
version="2.0">

    <persistence-unit name="jpaDemo">
        <provider>org.hibernate.ejb.HibernatePersistence</provider>
        <mapping-file>META-INF/orm.xml</mapping-file>
        <properties>
            <!-- standard properties -->
            <property name="javax.persistence.jdbc.url" value="jdbc:h2:./target/h2db/ejava"/>
            <property name="javax.persistence.jdbc.driver" value="org.h2.Driver"/>
            <property name="javax.persistence.jdbc.user" value="sa"/>
            <property name="javax.persistence.jdbc.password" value=""/>

            <!-- hibernate-specific properties -->
            <property name="hibernate.dialect" value="org.hibernate.dialect.H2Dialect"/>
            <property name="hibernate.hbm2ddl.auto" value="create"/>
            <property name="hibernate.show_sql" value="true"/>
            <property name="hibernate.format_sql" value="true"/>
            <!-- set to 0 to improve error messages when needed
            <property name="hibernate.jdbc.batch_size" value="0"/>            
             -->
        </properties>
    </persistence-unit>
</persistence>

Above example defines properties for entity manager to establish physical connections to database

public interface javax.persistence.EntityManager{
...
}
        
Author author = new Author();

author.setFirstName("dr");
author.setLastName("seuss");
author.setSubject("children");
author.setPublishDate(new Date());
log.debug("creating author:" + author);
em.persist(author);
log.debug("created author:" + author);
-creating author:ejava.examples.daoex.bo.Author@17e7691, id=0, fn=dr, ln=seuss, subject=children, pdate=Sun Sep 16 10:14:32 EDT 2012, version=0
-created author:ejava.examples.daoex.bo.Author@17e7691, id=50, fn=dr, ln=seuss, subject=children, pdate=Sun Sep 16 10:14:32 EDT 2012, version=0


//create initial author
Author author = new Author();
...
em.persist(author);
//create detached author with changes
Author author2 = new Author(author.getId());
author2.setFirstName("updated " + author.getFirstName());
...
//merge changes 
Author tmp = em.merge(author2);
em.getTransaction().begin();
em.getTransaction().commit();
...
//verify results
assertFalse("author2 is managed", em.contains(author2));
assertTrue("tmp Author is not managed", em.contains(tmp));
assertSame("merged result not existing managed", author, tmp);
...
//verify changes were made to the DB
Author author3 = em.find(Author.class, author.getId());
assertEquals("updated " + firstName, author3.getFirstName());            


em.persist(author);
//callers can detach entity from persistence context
log.debug("em.contains(author)="+em.contains(author));
log.debug("detaching author");
em.getTransaction().begin();
em.flush();
em.detach(author);
log.debug("em.contains(author)="+em.contains(author));
em.getTransaction().commit();
//changes to detached entities do not change database
author.setFirstName("foo");
em.getTransaction().begin();
em.getTransaction().commit();
Author author2 = em.find(Author.class, author.getId());
log.debug("author.firstName=" + author.getFirstName());
log.debug("author2.firstName=" + author2.getFirstName());
assertFalse("unexpected name change", 
        author.getFirstName().equals(author2.getFirstName()));
-em.contains(author)=true
-detaching author
-em.contains(author)=false
-author.firstName=foo
-author2.firstName=dr


em.persist(author);
em.getTransaction().begin();
em.getTransaction().commit();
//change DB state out-of-band from the cache
em.getTransaction().begin();
String newName="foo";
int count=em.createQuery(
        "update jpaAuthor a set a.firstName=:name where a.id=:id")
    .setParameter("id", author.getId())
    .setParameter("name", newName)
    .executeUpdate();
em.getTransaction().commit();
assertEquals("unexpected count", 1, count);
//object state becomes stale when DB changed out-of-band
log.debug("author.firstName=" + author.getFirstName());
assertFalse("unexpected name", author.getFirstName().equals(newName));
//get the cached object back in sync
log.debug("calling refresh");
em.refresh(author);
log.debug("author.firstName=" + author.getFirstName());
assertEquals("unexpected name", newName, author.getFirstName());
-author.firstName=dr
-calling refresh
-author.firstName=foo
        
src
|-- main
|   |-- java
|   |   `-- ejava
|   |       `-- examples
|   |           `-- daoex
|   |               |-- AuthorDAO.java
|   |               |-- bo
|   |               |   `-- Author.java
|   |               |-- DAOException.java
|   |               `-- jpa
|   |                   `-- JPAAuthorDAO.java
|   `-- resources
|       `-- META-INF
|           |-- orm.xml
|           `-- persistence.xml (could be placed in src/test branch)
`-- test
    |-- java
    |   `-- ejava
    |       `-- examples
    |           `-- daoex
    |               `-- jpa
    |                   |-- JPAAuthorDAOTest.java
    |                   |-- JPACRUDTest.java
    |                   `-- JPATestBase.java
    `-- resources
        |-- hibernate.properties (optional)
        `-- log4j.xml