solomax commented on code in PR #144:
URL: https://github.com/apache/openjpa/pull/144#discussion_r3801431795


##########
openjpa-persistence/src/main/java/org/apache/openjpa/persistence/EntityManagerFactoryImpl.java:
##########
@@ -477,7 +823,160 @@ public boolean isLoaded(Object entity, String attribute) {
         return (OpenJPAPersistenceUtil.isManagedBy(this, entity) &&
                 (OpenJPAPersistenceUtil.isLoaded(entity, attribute) == 
LoadState.LOADED));
     }
-
+    
+    @Override
+    public <E> boolean isLoaded(E entity, Attribute<? super E, ?> attribute) {
+       return isLoaded(entity, attribute.getName());
+    }
+    
+    @Override
+    public SchemaManager getSchemaManager() {
+       if (!this.isOpen()) {
+               throw new IllegalStateException("EntityManagerFactory is 
closed.");
+       }
+       return new SchemaManagerImpl(_factory);
+    }
+    
+    @Override
+    @SuppressWarnings("unchecked")
+    public <R> R callInTransaction(Function<EntityManager, R> work) {
+       EntityManager em = createEntityManager();
+       boolean startedTransaction = false;
+       boolean jtaTransaction = getTransactionType() == 
PersistenceUnitTransactionType.JTA;
+       Broker broker = em.unwrap(Broker.class);
+       try {
+               if (jtaTransaction) {
+                       if (!broker.syncWithManagedTransaction()) {
+                               broker.begin();
+                               startedTransaction = true;
+                       }
+               } else {
+                       em.getTransaction().begin();
+                       startedTransaction = true;
+               }
+               R result = work.apply(em);
+               if (startedTransaction) {
+                       if (jtaTransaction) {
+                               broker.commit();
+                       } else {
+                               em.getTransaction().commit();
+                       }
+               }
+               // For unenhanced (runtime-subclassed) entities, the user's 
function
+               // may return an original POJO that was passed to persist().
+               // Entities loaded via find() on other EMs are subclass 
instances,
+               // causing getClass() mismatches in equals(). To ensure 
consistent
+               // class identity, re-find managed entities from the database 
so that
+               // the returned instance is a subclass (matching what find() 
returns).
+               if (result != null && em.contains(result)) {
+                       try {
+                               Object id = 
getPersistenceUnitUtil().getIdentifier(result);
+                               if (id != null) {
+                                       Class<R> entityClass = (Class<R>) 
result.getClass();
+                                       em.clear();
+                                       R refound = em.find(entityClass, id);
+                                       if (refound != null) {
+                                               result = refound;
+                                       }
+                               }
+                       } catch (Exception e) {
+                               // If re-find fails, return original result
+                       }
+               }
+               return result;
+       } catch (Exception ex) {
+               if (jtaTransaction) {
+                       broker.rollback();
+               } else {
+                       try {
+                               em.getTransaction().rollback();
+                       } catch (Exception rollbackEx) {
+                               // Transaction may already be rolled back
+                       }
+               }
+               throw new UserException(ex.getMessage(), ex);
+       } finally {
+               em.close();
+       }
+    }
+    
+    @Override
+    public void runInTransaction(Consumer<EntityManager> work) {
+       callInTransaction(em -> {
+               work.accept(em);
+               return null;
+       });
+    }
+    
+    @Override
+    public <T> Class<? extends T> getClass(T entity) {
+       if (!OpenJPAPersistenceUtil.isManagedBy(this, entity)) {
+               throw new 
jakarta.persistence.PersistenceException(_loc.get("invalid_entity_argument",
+                    "getClass", entity == null ? "null" : 
Exceptions.toString(entity)).getMessage());
+       }
+       return OpenJPAPersistenceUtil.getClass(this, entity);
+    }
+    
+    @Override
+    public <R> Map<String, TypedQueryReference<R>> getNamedQueries(Class<R> 
resultType) {
+       throw new UnsupportedOperationException("Not yet implemented (JPA 
3.2)");
+    }
+    
+    @Override
+    public PersistenceUnitTransactionType getTransactionType() {
+       return 
"managed".equalsIgnoreCase(_factory.getConfiguration().getTransactionMode())
+                       ? PersistenceUnitTransactionType.JTA
+                       : PersistenceUnitTransactionType.RESOURCE_LOCAL;
+    }
+    
+    @Override
+    public Object getVersion(Object entity) {
+       if (!OpenJPAPersistenceUtil.isManagedBy(this, entity)) {
+               throw new 
IllegalArgumentException(_loc.get("invalid_entity_argument",

Review Comment:
   fixed



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: [email protected]

For queries about this service, please contact Infrastructure at:
[email protected]

Reply via email to