001: package org.compass.gps.device.jpa;
002:
003: import javax.persistence.EntityManager;
004: import javax.persistence.EntityManagerFactory;
005: import javax.persistence.PersistenceException;
006:
007: import org.apache.commons.logging.Log;
008: import org.apache.commons.logging.LogFactory;
009:
010: /**
011: * A simple base class for {@link EntityManagerWrapper} implementations. Calls the subclasses
012: * for <code>EntityManager</code>, and an optioan <code>EntityTransaction</code>. Takes care of
013: * all the rest.
014: *
015: * @author kimchy
016: */
017: public abstract class AbstractEntityManagerWrapper implements
018: EntityManagerWrapper {
019:
020: protected Log log = LogFactory.getLog(getClass());
021:
022: protected EntityManagerFactory entityManagerFactory;
023:
024: protected EntityManager entityManager;
025:
026: public void setUp(EntityManagerFactory entityManagerFactory) {
027: this .entityManagerFactory = entityManagerFactory;
028: }
029:
030: public EntityManager getEntityManager() {
031: if (entityManager == null) {
032: throw new IllegalStateException(
033: "Must be called between open and close");
034: }
035: return this .entityManager;
036: }
037:
038: public void open() throws JpaGpsDeviceException,
039: PersistenceException {
040: doCreateEntityManager();
041: beginTransaction();
042: }
043:
044: public void close() throws JpaGpsDeviceException,
045: PersistenceException {
046: try {
047: commitTransaction();
048: } finally {
049: if (shouldCloseEntityManager()) {
050: try {
051: entityManager.close();
052: } catch (PersistenceException e) {
053: log.warn("Failed to close JPA EntityManager", e);
054: } finally {
055: entityManager = null;
056: }
057: }
058: }
059: }
060:
061: public void closeOnError() throws JpaGpsDeviceException {
062: try {
063: rollbackTransaction();
064: } catch (PersistenceException e) {
065: log.warn("Failed to rollback JPA transaction, ignoring", e);
066: }
067: if (shouldCloseEntityManager()) {
068: try {
069: if (entityManager != null) {
070: entityManager.close();
071: }
072: } catch (PersistenceException e) {
073: log.warn("Failed to close JPA EntityManager, ignoring",
074: e);
075: } finally {
076: entityManager = null;
077: }
078: }
079: }
080:
081: public EntityManagerWrapper newInstance() {
082: try {
083: AbstractEntityManagerWrapper copy = getClass()
084: .newInstance();
085: copy.entityManagerFactory = entityManagerFactory;
086: return copy;
087: } catch (Exception e) {
088: throw new JpaGpsDeviceException(
089: "Failed to create new wrapper", e);
090: }
091: }
092:
093: protected void doCreateEntityManager() throws PersistenceException {
094: entityManager = entityManagerFactory.createEntityManager();
095: }
096:
097: protected abstract void beginTransaction()
098: throws PersistenceException;
099:
100: protected abstract void commitTransaction()
101: throws PersistenceException;
102:
103: protected abstract void rollbackTransaction()
104: throws PersistenceException;
105:
106: protected abstract boolean shouldCloseEntityManager();
107: }
|