-->
These old forums are deprecated now and set to read-only. We are waiting for you on our new forums!
More modern, Discourse-based and with GitHub/Google/Twitter authentication built-in.

All times are UTC - 5 hours [ DST ]



Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 7 posts ] 
Author Message
 Post subject: @PersistenceContext(type=TRANSACTION) ignored
PostPosted: Thu Feb 25, 2010 10:47 am 
Newbie

Joined: Thu Feb 25, 2010 10:11 am
Posts: 2
Hi. I'm having a problem using the Hibernate JPA implementation with Spring transactions / Tomcat. I think the following code should throw a TransactionRequiredException if save is called when not in a transaction.

Code:
public class MyObjDAO {
    @PersistenceContext(type=PersistenceContextType.TRANSACTION)
    private EntityManager em;
   
    public void save(MyObj obj) {
        em.persist(obj);
    }
}


However, no exception is thrown, and the application is completely unaware that nothing gets saved to the database.

Looking at how org.hibernate.ejb.EntityManagerFactoryImpl is implemented it seems it will always set the type to EXTENDED.

Code:
   public EntityManager createEntityManager(Map map) {
      //TODO support discardOnClose, persistencecontexttype?, interceptor,
      return new EntityManagerImpl(
            this, PersistenceContextType.EXTENDED, transactionType,
            discardOnClose, sessionInterceptorClass, map
      );
   }


From the code it looks like persistencecontexttype will always be EXTENDED for EntityManager objects created using the EntityManagerFactory.

Can anyone confirm this? If so this would seem to be a bug.

I'm using hibernate 3.5 b4 with Spring 3.0.1's LocalContainerEntityManagerFactoryBean and I'm guessing there is a good chance this is in fact a bug in Spring. It's not clear to me which out of Spring / Hibernate is responsible for processing the PersistenceContext annotation so if anyone could explain this that would be great also.


Top
 Profile  
 
 Post subject: Re: @PersistenceContext(type=TRANSACTION) ignored
PostPosted: Wed Jun 16, 2010 1:34 pm 
Newbie

Joined: Tue Mar 23, 2010 7:20 pm
Posts: 2
No response? I'm having a similar issue with this and It'd be helpful if anyone can confirm that Hibernate only supports PersistenceContextType.EXTENDED and doesn't support PersistenceContextType.TRANSACTION.


Top
 Profile  
 
 Post subject: Re: @PersistenceContext(type=TRANSACTION) ignored
PostPosted: Wed Jun 30, 2010 4:44 am 
Newbie

Joined: Tue May 18, 2010 5:39 am
Posts: 19
I am having the same issues. Can someone help by replying and suggesting what should be done if one needs to throw a Txn req exception while doing a persist on an entitymanager ?

I think if an or (||) instead of an and clause is used in AbstractEntityManagerImpl.checkTransactionNeeded() , then it should solve it without need of mentioning PersistenceContextType as TRANSACTION. isTransactionInProgress() will tell that the tnx is not in progresss.
Code:
private void checkTransactionNeeded() {
      if ( persistenceContextType == PersistenceContextType.TRANSACTION && ! isTransactionInProgress() ) {
         //no need to mark as rollback, no tx in progress
         throw new TransactionRequiredException(
               "no transaction is in progress for a TRANSACTION type persistence context"
         );
      }
   }

Thanks,

_________________
AG
http://anshuiitk.blogspot.com


Top
 Profile  
 
 Post subject: Re: @PersistenceContext(type=TRANSACTION) ignored
PostPosted: Wed Jun 30, 2010 12:24 pm 
Newbie

Joined: Tue May 18, 2010 5:39 am
Posts: 19
I think i have the solution : I am using spring with hibernate and spring does the transaction management for my application. Can some expert suggest this solution is good enough (atleast it works).
Code:
class SomeGenericDAO  {
    @PersistenceContext
    private EntityManager entityManager;
    @Autowired
    private EntityManagerFactory entityManagerFactory;

    public <T> T persist(T modelObject) {
        checkTransactionNeeded();
        entityManager.persist(modelObject);
        return modelObject;
    }

     private void checkTransactionNeeded() {
        EntityManagerHolder emHolder = (EntityManagerHolder) TransactionSynchronizationManager.getResource(entityManagerFactory);
        if (emHolder == null) {
            throw new TransactionRequiredException("no transaction is in progress");
        }
    }
}


The caller for persist is responsible to make sure that the spring transaction is not around. If it is not then a javax.persistence.TransactionRequiredException (Bad API used but may be a custom exception) is thrown.

Atleast we know the pieces of code (hidden inside autowired beans ? ) which are executed without transction boundaries.

_________________
AG
http://anshuiitk.blogspot.com


Top
 Profile  
 
 Post subject: Re: @PersistenceContext(type=TRANSACTION) ignored
PostPosted: Wed Jun 30, 2010 3:19 pm 
Newbie

Joined: Thu Feb 25, 2010 10:11 am
Posts: 2
anshuiitk, I think your solution will work but doesn't it invovle having to introduce a method call for every method which updates the database in every dao? I think spring / hibernate are meant to take of the boiler plate code for you so I don't think there is a bug somewhere here.


Top
 Profile  
 
 Post subject: Re: @PersistenceContext(type=TRANSACTION) ignored
PostPosted: Wed Jun 30, 2010 5:38 pm 
Newbie

Joined: Tue May 18, 2010 5:39 am
Posts: 19
I dont claim it to be a bug. What i say is hibernate does not supports entitymanager with persistencecontexttype as transaction, and hence all the problems, the solution suggested is a workaround and It (the boiler plate code ? ) should go inside hibernate.

If you look at the entitymanager.persist() methods implementation it does throws a TransactionRequiredException – if invoked on a container managed entity manager of type PersistenceContextType.TRANSACTION and there is no transaction. But because we cannot change hibernate code, hence would have to live with the patches like these :)

_________________
AG
http://anshuiitk.blogspot.com


Top
 Profile  
 
 Post subject: Re: @PersistenceContext(type=TRANSACTION) ignored
PostPosted: Thu Aug 19, 2010 10:55 am 
Newbie

Joined: Mon Sep 29, 2008 7:18 pm
Posts: 5
Anyone figure this out? I am having exactly the same problem:data is persisted in the context, but not into the database.
Code:
@WebService() 
@Stateless() 
public class UserHandler { 
    @PersistenceContext(unitName = "ThompCo") 
    private EntityManager myEm; 
 
    /**
     * Web service operation
     */ 
    @WebMethod(operationName = "updateUser") 
    @TransactionAttribute(TransactionAttributeType.REQUIRES_NEW) 
    public Boolean updateUser(@WebParam(name = "user") UserTo user) { 
        try { 
            TransferObjectHelper.persist(user, myEm); 
        } catch (Exception e) { 
            return false; 
        } 
        return true; 
    }




Here is the persist method (note that I have added some convolution out of desperation):
Code:
public static boolean persist(final UserTo user, EntityManager em) { 
        User u = getUser(user.username, em); 
 
        if (u != null) { 
            if (!u.getPassword().equals(user.password)) { 
                ServerDb.execute("set password for '" + user.username + 
                                 "' = password('" + user.password + "')"); 
            } 
 
            u.setName(user.actualName); 
            u.setPassword(user.password); 
            u.setUserName(user.username); 
            u.setCustomer(ServerDb.getCustomerId(user.customer, em)); 
 
            Query query = em.createNamedQuery("Columnheading.findAll"); 
            List<Columnheading> columnHeadingList = query.getResultList(); 
 
            u.getColumnheadingCollection().clear(); 
            for (Columnheading availCol : columnHeadingList) { 
                availCol.getUserCollection().remove(u); 
 
                for (String userCol : user.columnHeadings) { 
                    if (userCol.equals(availCol.getOutputName())) { 
                        u.getColumnheadingCollection().add(availCol); 
                        availCol.getUserCollection().add(u); 
                        break; 
                    } 
                } 
 
                em.merge(availCol); 
            } 
 
            Query queryPermissions = em.createNamedQuery( 
                    "Systempermission.findAll"); 
            List<Systempermission> permissionList = queryPermissions. 
                    getResultList(); 
 
            u.getSystempermissionCollection().clear(); 
            for (Systempermission availPermission : permissionList) { 
                availPermission.getUserCollection().remove(u); 
 
                for (String userPermission : user.permissions) { 
                    if (userPermission.equals( 
                            availPermission.getPermissionName())) { 
                        u.getSystempermissionCollection().add(availPermission); 
                        availPermission.getUserCollection().add(u); 
                        break; 
                    } 
                } 
 
                em.merge(availPermission); 
            } 
 
            Query queryLoggers = em.createNamedQuery("Datalogger.findAll"); 
            List<Datalogger> loggerList = queryLoggers.getResultList(); 
 
            u.getDataloggerCollection().clear(); 
            for (Datalogger availLogger : loggerList) { 
                availLogger.getUserCollection().remove(u); 
 
                for (String userLogger : user.loggers) { 
                    if (userLogger.equals(availLogger.getName())) { 
                        u.getDataloggerCollection().add(availLogger); 
                        availLogger.getUserCollection().add(u); 
                        break; 
                    } 
                } 
 
                em.merge(availLogger); 
            } 
 
            em.merge(u); 
            em.flush(); 
            return true; 
        } else { 
            return false; 
        } 
    } 


I only seem to see this problem with containers of entities...


Top
 Profile  
 
Display posts from previous:  Sort by  
Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 7 posts ] 

All times are UTC - 5 hours [ DST ]


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum

Search for:
© Copyright 2014, Red Hat Inc. All rights reserved. JBoss and Hibernate are registered trademarks and servicemarks of Red Hat, Inc.