On Java Development

All things related to Java development, from the perspective of a caveman.

When to close the EntityManager

without comments

Introduction

The post addresses the question of when to close the JPA Entity Manager. The information presented will show that the answer actually depends on many things, ranging from the use of JSE vs JEE, to how the JTA transaction unit is coded.

 

JSE vs JEE

First, a brief overview of the differences between an application built using JSE and one built using JEE standards and technologies.

 

JSE

The simplest way of describing JSE is to say that it consists of the base packages that come with the Java Runtime Environment (JRE) and Java Development Kit (JDK). These packages are listed below.

General purpose packages

  • java.lang
  • java.io
  • java.nio
  • java.math
  • java.net
  • java.text
  • java.util

Special purpose packages

  • java.applet
  • java.beans
  • java.awt
  • java.rmi
  • java.security
  • java.sql
  • javax.rmi
  • javax.swing
  • javax.swing.text.html.parser
  • javax.xml.bind.annotation

OMG packages

  • org.omg.CORBA
  • org.omg.PortableInterceptor

The packages are enough to allow for the development of desktop applications, i.e. “fat clients”. With the addition of external jar-files not provided by the java platform, database connectivity is even possible. When you see JSE, think “fat client” development.

 

JEE

JEE is represented by a set of packages that are used to develop enterprise applications. These will be of the type that run on servers. These packages extend the functionality of JSE and are listed below.

General APIs

  • javax.servlet.*
  • javax.websocket.*
  • javax.faces.*
  • javax.faces.component.*
  • javax.el.*
  • javax.enterprise.inject.*
  • javax.enterprise.context.*
  • javax.ejb.*
  • javax.validation.*
  • javax.persistence.*
  • javax.transaction.*
  • javax.security.auth.message.*
  • javax.enterprise.concurrent.*
  • javax.jms.*
  • javax.batch.api.*
  • javax.resource.*

The packages are used in the development of web applications which include other technologies such as HTML, JSP, JSF, JDBC, Spring and Hibernate.

JSE and JEE are different Java platforms used for application development while JEE extends the capabilities of JSE. The design of the resulting application will reflect different design and deployment concerns.

 

The Java Persistence API (JPA) and the Entity Manager

The Java Persistence API (JPA) is a Java application programming interface specification that describes the management of relational data in applications using Java Platform, Standard Edition (JSE) and Java Platform, Enterprise Edition (JEE).

Entity Managers in Java SE environments

JPA is available to JSE applications. Connections to the database is handled using the JPA Entity Manager. The JBoss Hibernate documentation describes its use as follows.

In a Java SE environment only extended context application-managed entity managers are available. You can retrieve an entity manger using the EntityManagerFactory API. Only resource-local entity managers are available. In other words, JTA transactions and persistence context propagation are not supported in Java SE (you will have to propagate the persistence context yourself, e.g. using the thread local session pattern popular in the Hibernate community).

Extended context means that a persistence context is created when the entity manager is retrieved (using EntityManagerFactory.createEntityManager(…) ) and closed when the entity manager is closed. Many resource-local transaction share the same persistence context, in this case.

It is apparent that in a JSE application, entity managers obtained using the EntityManagerFactory API where extra coding is required to persist the context entities to the database. Also, there are certain JPA configuration entries required for this behavior. In a JSE environment a non-JTA data source is used along with a transaction type of defined as ‘RESOURCE_LOCAL’.

For an application-managed entity manager, the persistence unit definition in web.xml is defined as shown. It is referenced by the entity manager.

Obtaining the entity manager then looks like this.

Note that the persistence session begins by starting a transaction, persisting the entity, committing the transaction and finally, the entity manager is closed.

 

Entity Managers in Java EE environments

Hibernate documentation describes the use of entity managers in a JEE environment as follows:

Container-managed entity manager

The most common and widely used entity manager in a Java EE environment is the container-managed entity manager. In this mode, the container is responsible for the opening and closing of the entity manager (this is transparent to the application). It is also responsible for transaction boundaries. A container-managed entity manager is obtained in an application through dependency injection or through JNDI lookup, A container-managed entity manger requires the use of a JTA transaction.

Application-managed entity manager

An application-managed entity manager allows you to control the entity manager in application code. This entity manager is retrieved through the EntityManagerFactory API. An application managed entity manager can be either involved in the current JTA transaction (a JTA entity manager), or the transaction may be controlled through the EntityTransaction API (a resource-local entity manager). The resource-local entity manager transaction maps to a direct resource transaction (i. e. in Hibernate’s case a JDBC transaction). The entity manager type (JTA or resource-local) is defined at configuration time, when setting up the entity manager factory.

For a container-managed entity manager, the persistence unit definition in web.xml is defined as shown.

Obtaining the entity manager then looks like this.

Again, there are certain JPA configuration entries required for this behavior. In a JEE environment a JTA data source is used along with a transaction type designation of ‘JTA’.

When persistence unit configuration is designated for “JTA” (as opposed to “RESOURCE_LOCAL”), the following rules apply.

  • You cannot use the EntityManagerFactory to get an EntityManager.
  • You can only get an EntityManager supplied by the container.
  • An EntityManager can be injected via the @PersistenceContext annotation only (not @PersistenceUnit).
  • You are not allowed to use @PersistenceUnit to refer to a unit of type JTA.
  • The EntityManager given by the container is a reference to the PersistenceContext/Cache associated with a JTA transaction.
  • If no JTA transaction is in progress, the EntityManager cannot be used because there is no PersistenceContext/Cache.
  • Everyone with an EntityManager reference to the same unit in the same transaction will automatically have a reference to the same PersistenceContext/Cache.
  • The PersistenceContext/Cache is flushed and cleared at JTA commit time ‘ApplicationPersistenceContext’ is defined in web/xml. It refers to the persistence unit having the same name that resides in ‘persistence.xml’.

 

Closing the Entity Manager

You now see that the answer to the question of when to close the entity manager depends on the persistence strategy being employed which will be governed by the underlying technologies the application is employing.

More details about the closing of the entity manager is provided by the JPA Specification, section 7.7 Application-managed Persistence Contexts.


When an application-managed entity manager is used, the application interacts directly with the persistence provider’s entity manager factory to manage the entity manager lifecycle and to obtain and destroy persistence contexts.

All such application-managed persistence contexts are extended in scope, and can span multiple transactions.

The EntityManagerFactory.createEntityManager method and the EntityManager close and isOpen methods are used to manage the lifecycle of an application-managed entity manager and its associated persistence context.

The extended persistence context exists from the point at which the entity manager has been created using EntityManagerFactory.createEntityManager until the entity manager is closed by means of EntityManager.close.

An extended persistence context obtained from the application-managed entity manager is a stand-alone persistence context it is not propagated with the transaction.

[…] The EntityManager.close method closes an entity manager to release its persistence context and other resources. After calling close, the application must not invoke any further methods on the EntityManager instance except for getTransaction and isOpen, or the IllegalStateException will be thrown. If the close method is invoked when a transaction is active, the persistence context remains managed until the transaction completes.

The EntityManager.isOpen method indicates whether the entity manager is open. The isOpen method returns true until the entity manager has been closed. To actually understand how this works it is vital to understand the relationship between the entity manager and the context.

 

How the Persistence Contexts work

There are different types of persistence contexts, depending on the type of application.

In the JSE application, the nature of the context is controlled by the developer.

In Java EE applications, you can have a transaction-scoped persistence context or an extended-persistence context.

As the name implies, the entity manager manages entities within the persistence context. When a first-level cache (session cache) is employed, when an entity is retrieved using HQL or JPQL, the entity manager will first look for the entity in its context. If not found, it will retrieve it from the database. All retrieval requests for that entity after that time will be returned from the cache.

When an application is employing a transaction-scoped persistence context, the first access to the entity manager causes it to check if the current JPA transaction is attached to a context. If not, the entity manager creates and attaches to itself a new context. Following this, the entity is read from the database and placed in that context. When the transaction ends by way of a commit or rollback operation, the context is invalidated and all entities within move into a detached state. They are now stateless.

In the context of baseproject and/or libertybase, the service class is responsible for obtaining the entity manager and orchestrating the use of any number of DAO instances as required. At the end of the I/O phase, the service class performs a commit, committing the entities to the database and essentially destroying the context until the next service is called at which time a new entity manager and new context is created.

This creates some interesting relationships, transaction-wise. For example, if a service method employs one or more DOAs within its transaction all I/O must execute successfully for the data to be persisted to the database. On the other hand, if the service class employs other service classes, then you end up with a multiple contexts and a nested transaction situation.

After describing this scenario, because the JPA specification states nested transactions are not required to be supported by the implementation of the API, this scenario should be avoided. Furthermore, a quick scan of JSR-317 Java Persistence API, Verion 2.0 for nested transactions reveal no information on the topic.

 
 

Resources

Java Persistence API
Interface EntityManager
Entity Managers in Java SE environments
JPA Configuration and Java coding

Written by admin

October 14th, 2015 at 1:23 pm

Posted in JPA

Leave a Reply

You must be logged in to post a comment.