JPA 2.1 – Features every developer should know

Features and Enhancements in JPA 2.1

Named Stored Procedure Query

Sometimes it is easier or more efficient to use a stored procedure to perform the operations within the database. Before JPA 2.1 the only way to call a stored procedure was to use a native query. The newly introduced @NamedStoredProcedureQuery can now be used to annotate a query to call the stored procedure. 

Stored Procedure Query

The Stored Procedure Query is an alternative way to implement a stored procedure call without using annotations. For this purpose the EntityManager was extended by the createStoredProcedureQuery(String procedureName, Class… resultClasses) method.
You can read more about it in How to call stored procedures in JPA – Part 2.
Attribute Converter
Attribute Converter provide a nice and easy way to define a custom mapping between your property on the entity and the database column. The only thing that is needed is a class that implements the AttributeConverter interface and is annotated with @Converter. You can find a more detailed introduction to Attribute Converter in JPA 2.1 – How to implement an Attribute Converter.
One of the most obvious ways to use an Attribute Converter is to implement a custom type mapping to persist a not supported data type like the new Java Date and Time API:  How to persist LocalDate and LocalDateTime with JPA.
Or you can use it to change an existing default mapping, as it was done in JPA 2.1 Attribute Converter – The better way to persist enums.
You could also keep the type and change the stored value to implement some business requirements like encryption: How to use a JPA Attribute Converter to encrypt your data.

Constructor Result Mapping

The @ConstructorResult annotation is a handy addition to the already existing @SqlResultSetMapping and can be used to map the result of a query to a constructor call.
You can read more about it in the constructor result mappings part of the result set mapping series.

Programmatic Named Queries

Before JPA 2.1 the @NamedQuery annotation was the only way to define named queries. A programmatic creation was not supported. This was changed with JPA 2.1. The EntityManager now provides the addNamedQuery(String name, Query query) method to do this.

Named Entity Graph

Lazy loading of relations between entities is a common pattern to load only the required information from the database and to improve the performance of the application. While this is a great feature as long as the related entities are not required, it creates additional load when the relations need to be initialized. There are multiple ways to initialize these lazy relations and using Named Entity Graphs is one of the better ones. 
The annotations @NamedEntityGraph@NamedAttributeNode and @NamedSubGraph allow us to define a graph of entities that will be loaded from the database. You can find a more detailed description on how to do this in JPA 2.1 Entity Graph – Part 1: Named entity graphs.

Entity Graph

Entity Graphs are the second option introduced with JPA 2.1 to define a graph of entities that shall be loaded from the database and their usage is similar to Named Entity Graphs. The only difference is that Entity Graphs are defined via a Java API and not via annotations. Therefore theEntityManager was extended by the createEntityGraph(Class rootType) method. This is explained in more detail in JPA 2.1 Entity Graph – Part 2: Define lazy/eager loading at runtime.

JPQL Enhancements

There were several enhancements to the JPQL which can come in handy. You can now use the keyword ON to define additional join parameters, call database functions by using FUNCTION and downcast entities with TREAT.

Criteria API Bulk Operations

Up to JPA 2.1 the Criteria API did not provide any support for update or delete operations. The only options available were to perform the update on an entity or to write a native query to update multiple records at once. As described in Criteria Update/Delete – The easy way to implement bulk operations with JPA2.1, the Criteria API was extended with CriteriaUpdate andCriteriaDelete to also support bulk write operations.

Unsynchronized Persistence Context

Using a synchronized persistence context to propagate every change to the database is the default approach in JPA. If you need more control about the database propagation, you can now use the unsynchronized persistence context. Therefore you need to provide the synchronization mode to the injection with @PersistenceContext(synchronization=SynchronizationType.UNSYNCHRONIZED). You then need to call EntityManager.joinTransaction() manually to synchronize the changes.

Generating DB Schema

Up to JPA 2.1 you needed to use vendor specific configuration parameter to define the database setup in the persistence.xml file. Starting from version 2.1 there is also a standard way to do this. Therefore the specification defines the following long list of parameters:
  • javax.persistence.schema-generation.database.action
  • javax.persistence.schema-generation.scripts.action
  • javax.persistence.schema-generation.create-source
  • javax.persistence.schema-generation.drop-source
  • javax.persistence.schema-generation.create-database-schemas
  • javax.persistence.schema-generation.scripts.create-target
  • javax.persistence.schema-generation.scripts.drop-target
  • javax.persistence.database-product-name
  • javax.persistence.database-major-version
  • javax.persistence.database-minor-version
  • javax.persistence.schema-generation.create-script-source
  • javax.persistence.schema-generation.drop-script-source
  • javax.persistence.schema-generation.connection
  • javax.persistence.sql-load-script-source
You can get a more detailed description of the different parameters and some examples how to use them to setup your database in Standardized schema generation and data loading with JPA 2.1.


Popular posts from this blog

PostgreSQL bytea and oid

MySQL as Hive metadata store

Microservices Architecture with Spring Boot in 15mins