How do I create a persistence.xml file for JPA and Hibernate?
I'm trying to use Hibernate JPA but I need to create my persistence.xml (so I can use the entity manager correctly). I am unsure of what to create and where to place it.
This is how my hibernate.cfg.xml in 'Core' mode configured. I'm using Eclipse Java EE IDE Web Developers (Indigo Release):
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE hibernate-configuration PUBLIC
开发者_如何学C "-//Hibernate/Hibernate Configuration DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
<session-factory>
<property name="hibernate.connection.driver_class">com.mysql.jdbc.Driver</property>
<property name="hibernate.connection.password">XXXXXX</property>
<property name="hibernate.connection.url">jdbc:mysql://<hostname>/<database></property>
<property name="hibernate.connection.username">XXXXX</property>
<property name="hibernate.default_schema">XXXXXX</property>
<property name="hibernate.dialect">org.hibernate.dialect.MySQLDialect</property>
</session-factory>
</hibernate-configuration>
JPA persistence XML file location
Traditionally, the persistence.xml is located in a META-INF
folder that needs to reside in the root of the Java classpath. If you’re using Maven, you can store it in the resources
folder, like this:
src/main/resources/META-INF/persistence.xml
JPA persistence XML file structure
The `persistence.xml configuration file is structured as follows:
<?xml version="1.0" encoding="UTF-8"?>
<persistence version="2.2"
xmlns="http://xmlns.jcp.org/xml/ns/persistence"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/persistence
http://xmlns.jcp.org/xml/ns/persistence/persistence_2_2.xsd">
<persistence-unit
name="HypersistenceOptimizer"
transaction-type="JTA">
<description>
Hypersistence Optimizer is a dynamic analyzing tool that can scan
your JPA and Hibernate application and provide you tips about the
changes you need to make to entity mappings, configurations, queries,
and Persistence Context actions to speed up your data access layer.
</description>
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
<jta-data-source>java:global/jdbc/default</jta-data-source>
<properties>
<property
name="hibernate.transaction.jta.platform"
value="SunOne"
/>
</properties>
</persistence-unit>
</persistence>
The persistence
tag is the root XML element, and it defines the JPA version and the XML schema used to validate the persistence.xml
configuration file.
persistence-unit
The persistence-unit
element defines the name of the associated JPA Persistence Unit, which you can later use to reference it when using the @PersistenceUnit
JPA annotation to inject the associated EntityManagerFactory
instance:
@PersistenceUnit(name = "HypersistenceOptimizer")
private EntityManagerFactory entityManagerFactory;
The transaction-type
attribute defines the JPA transaction strategy, and it can take one of the following two values:
JTA
RESOURCE_LOCAL
Traditionally, Java EE applications used JTA by default, which requires having a JTA transaction manager that uses the 2PC (Two-Phase Commit) protocol to apply changes atomically to multiple sources of data (e.g., database systems, JMS queues, Caches).
If you want to propagate changes to a single data source, then you don't need JTA, so the RESOURCE_LOCAL
transaction type is a much more efficient alternative. For instance, by default, Spring applications use RESOURCE_LOCAL
transactions, and to use JTA
, you need to explicitly choose the JtaTranscationManager
Spring bean.
description
The description
element allows you to provide more details about the goals of the current Persistence Unit.
provider
The provider
XML element defines the fully-qualified class name implementing the JPA PersistenceProvider
interface.
If you are using Hibernate 4.3 or newer versions, then you need to use the
org.hibernate.jpa.HibernatePersistenceProvider
class name.If you are using Hibernate 4.2 or older versions, then you need to use the
org.hibernate.ejb.HibernatePersistence
class name instead.
jta-data-source and non-jta-data-source
It's very unusual that the JPA spec defines two different XML tags to provide the JNDI DataSource
name. There should have been a single data-source
attribute for that since the transaction-type
already specifies whether JTA is used or not.
No, if you're using JTA, you can use the jta-data-source
to specify the JNDI name for the associated JTA DataSource
, while for RESOURCE_LOCAL
, you need to use the non-jta-data-source
.
If you're using Hibernate, you can also use the
hibernate.connection.datasource
configuration property to specify the JDBCDataSource
to be used.
properties
The properties
element allows you to define JPA or JPA provider-specific properties to configure:
- the Hibernate
Dialect
- the JTA transaction platform (e.g., GlassFish, JBoss, Bitronix, Atomikos)
- whether the database schema should be auto-generated
- whether Hibernate should skip the auto-commit check for RESOURCE_LOCAL transactions
- activate the slow SQL query log
- and many more properties you can find in the
org.hibernate.cfg.AvailableSettings
interface.
Entity mapping settings
By default, Hibernate is capable of finding the JPA entity classes based on the presence of the @Entity
annotation, so you don't need to declare the entity classes.
However, if you want to explicitly set the entity classes to be be used, and exclude any other entity classes found on the current Java classpath, then you need to set the exclude-unlisted-classes
element to the value of true
:
<exclude-unlisted-classes>true</exclude-unlisted-classes>
class
After setting the exclude-unlisted-classes
XML element above, you need to specify the list of entity classes registered by the current Persistence Unit via the class
XML element:
<class>io.hypersistence.optimizer.forum.domain.Post</class>
<class>io.hypersistence.optimizer.forum.domain.PostComment</class>
<class>io.hypersistence.optimizer.forum.domain.PostDetails</class>
<class>io.hypersistence.optimizer.forum.domain.Tag</class>
The vast majority of JPA and Hibernate applications use annotations to build the object-relational mapping metadata. However, even if you are using annotations, you can still use XML mappings to override the static annotation metadata with the one provided via an orm.xml
configuration file.
mapping-fileFor instance, you can use the
SEQUENCE
identifier generator by default using the@SequenceGenerator
annotation and substitute that withIDENTITY
for MySQL, which does not support database sequences.
By default, the orm.xml
configuration file is located in the META-INF
folder. If you want to use a different file location, you can use the mapping-file
XML element in the persistence.xml
file, like this:
<mapping-file>file:///D:/Vlad/Work/Examples/mappings/orm.xml</mapping-file>
jar-file
Bu default, the JPA provider is going to scan the current Java classpath to load entity classes or XML mappings. If you want to provide one or more JAR files to be scanned, you can use the jar-file
element, like this:
<jar-file>lib/hypersistence-optimizer-glassfish-hibernate-example.jar</jar-file>
shared-cache-mode
The shared-cache-mode
element allows you to define the SharedCacheMode
strategy for storing entities in the second-level cache, and it can take one of the following values:
ALL
- stores all entities in the second-level cache,NONE
- entities are not stored in the second-level cache,ENABLE_SELECTIVE
- no entity is cached by default, except for the ones marked with the@Cacheable(true)
annotation, which are going to be cachedDISABLE_SELECTIVE
- all entities are cached by default, except for the ones marked with the@Cacheable(false)
annotationUNSPECIFIED
- uses the JPA provider default caching strategy. This is also the default value that's used when theshared-cache-mode
element is not set.
You can also override the shared-cache-mode
strategy programmatically using the javax.persistence.cache.storeMode
property, like this:
EntityManagerFactory entityManagerFactory = Persistence
.createEntityManagerFactory(
"HypersistenceOptimizer",
Collections.singletonMap(
"javax.persistence.cache.storeMode",
SharedCacheMode.ENABLE_SELECTIVE
)
);
validation-mode
The validation-mode
XML element specifies the ValidationMode
strategy, which instructs the JPA provider whether it should check the entities Bean Validation at runtime.
The validation-mode
element can take the following values:
AUTO
- If a Bean Validation provider is found in the current Java classpath, it will be registered automatically, and all entities are going to be validated. If no Bean Validation provider is found, entities are not validated. This is the default value.CALLBACK
- Entities must always be validated by a Bean Validation provider. If the JPA provider does no found a Bean Validation implementation on the classpath, the bootstrap process will fail.NONE
- Entities are not validated even if a Bean Validation provider is found on the classpath.
You can also override the validation-mode
strategy programmatically using the javax.persistence.validation.mode
property, like this:
EntityManagerFactory entityManagerFactory = Persistence
.createEntityManagerFactory(
"HypersistenceOptimizer",
Collections.singletonMap(
"javax.persistence.validation.mode",
ValidationMode.CALLBACK
)
);
Create a persistence.xml file that resides in the META-INF folder.
Example:
<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="sample">
<provider>org.hibernate.ejb.HibernatePersistence</provider>
<jta-data-source>java:/DefaultDS</jta-data-source>
<mapping-file>ormap.xml</mapping-file>
<jar-file>MyApp.jar</jar-file>
<class>org.acme.Employee</class>
<class>org.acme.Person</class>
<class>org.acme.Address</class>
<properties>
<property name="hibernate.connection.driver_class">com.mysql.jdbc.Driver</property>
<property name="hibernate.connection.password">XXXXXX</property>
<property name="hibernate.connection.url">jdbc:mysql://<hostname>/<database></property>
<property name="hibernate.connection.username">XXXXX</property>
<property name="hibernate.default_schema">XXXXXX</property>
<property name="hibernate.dialect">org.hibernate.dialect.MySQLDialect</property>
</properties>
</persistence-unit>
</persistence>
In intellij, one good approach would be to just go to "File > Project structure > Facets". Then Add new persistence.xml in src/main/resources/META-INF/persistence.xml. Click apply and it will be created for you.
精彩评论