I've recently started working with JPA on the Google App Engine. In reading some examples, I've noticed a couple of variations in the way objects are persisted. In one case, I've seen something like this:
entityManager.getTransaction().begin();
entityManager.persist(object);
entityManager.getTransaction().commit();
In other cases, I don't see the use of getTransaction()
. I simply see entityManager.persist(object)
. When is it appropriate to use getTransaction()
?
If you use container managed EntityManager
then you're using JTA transactions. Hence, you don't need to (more precisely - you can not) interfere with EntityManager
's transactions fetched using entityManager.getTransaction()
. The JTA starts and commits your transaction.
If you use application managed EntityManager
and you don't want to be in part of JTA transaction, then you need to manage them for yourself (it's called a resource-local entity manager).
Most typically, application managed EntityManager
which works with EntityManager.getTransaction()
is used in Java SE environment.
EDIT: You might be interested in secion 7.5 Controlling Transactions from the JPA 2.0 specification.
In GAE there is no Java EE/JTA so ignore terms such as bean managed transaction (BMT), and container managed transactions (CMT).
Your work is either transactional (where you want multiple objects to go to the datastore at once, or all to fail - this is where you have getTransaction() used), or nontransactional (where everything goes to the datastore one by one, and the failure of one persist doesn't affect others - this is where you just call persist()/merge()/remove()).
Google App Engine has its transaction management (https://developers.google.com/appengine/docs/java/datastore/transactions) but the JPA transaction interface isn't aware of some of the GAE underlying functionalities (i.e. entity groups).
So it’s up to your application to decide which operations to perform in a transaction and which not. You should put in a transaction operations that have to be executed atomically.
Remember as a best practice to perform cascading actions and relationship operations in a transaction because JPA might trigger many queries and it could lead to an inconsistent data situation.
Example of using transaction with JPA2:
import javax.persistence.EntityTransaction;
EntityTransaction txn = em.getTransaction();
txn.begin();
try {
//do something with your database
txn.commit();
}
finally {
if (txn.isActive())
txn.rollback();
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With