Hi,

I've created a desktop application using OpenJPA 1.2.1. Due to the large
amount of data in the DB lazy fetching is basically a must. Large
collections in some entity classes aren't accessed right away after
retrieving the objects from the DB so the entity manager has the remain
open. Because of this I created a singleton construction which is being used
throughout the application to supply the entity manager.

public enum JPAEntityManager {
    INSTANCE;

    private EntityManagerFactory entityManagerFactory =
Persistence.createEntityManagerFactory("MPSFPU");
    private EntityManager entityManager =
entityManagerFactory.createEntityManager();

    public EntityManager getManager() {
        return entityManager;
    }

    public void terminate() {
        entityManager.close();
        entityManagerFactory.close();
    }
}

This method of working functions until the entity manager is called from two
different threads at the same time. Sometimes it works, sometimes I get an
error like the following (note the strange fact that it Weapon is the
problem but it is one of the known entities):

63  MPSFPU  INFO   [RunnableQueue-1] openjpa.Runtime - Starting OpenJPA
1.2.1
188  MPSFPU  INFO   [RunnableQueue-1] openjpa.jdbc.JDBC - Using dictionary
class "org.apache.openjpa.jdbc.sql.DerbyDictionary".
<openjpa-1.2.1-r752877:753278 nonfatal user error>
org.apache.openjpa.persistence.ArgumentException: An error occurred while
parsing the query filter "SELECT d FROM Weapon d WHERE d.type = 'gun'".
Error message: The name "Weapon" is not a recognized entity or identifier.
Perhaps you meant Weapon, which is a close match. Known entity names:
[Sensor, Weapon, Threat]
        at
org.apache.openjpa.kernel.exps.AbstractExpressionBuilder.parseException(AbstractExpressionBuilder.java:118)
        at
org.apache.openjpa.kernel.jpql.JPQLExpressionBuilder.getClassMetaData(JPQLExpressionBuilder.java:177)
        at
org.apache.openjpa.kernel.jpql.JPQLExpressionBuilder.resolveClassMetaData(JPQLExpressionBuilder.java:150)
        at
org.apache.openjpa.kernel.jpql.JPQLExpressionBuilder.getCandidateMetaData(JPQLExpressionBuilder.java:225)
        at
org.apache.openjpa.kernel.jpql.JPQLExpressionBuilder.getCandidateMetaData(JPQLExpressionBuilder.java:195)
        at
org.apache.openjpa.kernel.jpql.JPQLExpressionBuilder.getCandidateType(JPQLExpressionBuilder.java:188)
        at
org.apache.openjpa.kernel.jpql.JPQLExpressionBuilder.access$600(JPQLExpressionBuilder.java:69)
        at
org.apache.openjpa.kernel.jpql.JPQLExpressionBuilder$ParsedJPQL.populate(JPQLExpressionBuilder.java:1756)
        at
org.apache.openjpa.kernel.jpql.JPQLParser.populate(JPQLParser.java:56)
        at
org.apache.openjpa.kernel.ExpressionStoreQuery.populateFromCompilation(ExpressionStoreQuery.java:153)
        at
org.apache.openjpa.kernel.QueryImpl.newCompilation(QueryImpl.java:658)
        at
org.apache.openjpa.kernel.QueryImpl.compilationFromCache(QueryImpl.java:639)
        at
org.apache.openjpa.kernel.QueryImpl.compileForCompilation(QueryImpl.java:605)
        at
org.apache.openjpa.kernel.QueryImpl.compileForExecutor(QueryImpl.java:667)
        at
org.apache.openjpa.kernel.QueryImpl.getOperation(QueryImpl.java:1492)
        at
org.apache.openjpa.kernel.DelegatingQuery.getOperation(DelegatingQuery.java:123)
        at
org.apache.openjpa.persistence.QueryImpl.execute(QueryImpl.java:243)
        at
org.apache.openjpa.persistence.QueryImpl.getResultList(QueryImpl.java:294)
        at
com.thalesgroup.nl.mpsf.editor.AddDeviceTool.initDeviceList(AddDeviceTool.java:133)
        at
com.thalesgroup.nl.mpsf.editor.AddDeviceTool.<init>(AddDeviceTool.java:56)
        at
com.thalesgroup.nl.mpsf.editor.MPSFView$2$1.addDeviceEventListeners(MPSFView.java:148)
        at
com.thalesgroup.nl.mpsf.editor.MPSFView$2$1.run(MPSFView.java:131)
        at org.apache.batik.util.RunnableQueue.run(Unknown Source)
        at java.lang.Thread.run(Thread.java:595)

Sometimes it gives me the error about not being able to use the same entity
manager simultaneously by default instead. Settings the recommended
openjpa.Multithreaded property to true does however not fix the problem.

How can I work around this problem to make it work in a multi-threaded
environment?
If using the same entity manager this way isn't possible, what are my
options to prevent the use of eager fetching but still being able to
retrieve e.g. the collections data when required without having to
completely recreate the object again?
I thought about creating an entity manager for every single request and
simply not closing it but that doesn't seem like the right approach.

Yours,

Age
-- 
View this message in context: 
http://n2.nabble.com/EntityManager-used-in-multiple-threads-tp3662432p3662432.html
Sent from the OpenJPA Users mailing list archive at Nabble.com.

Reply via email to