-->
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.  [ 3 posts ] 
Author Message
 Post subject: Auto commit remains enabled in transaction
PostPosted: Thu Mar 22, 2012 10:14 am 
Newbie

Joined: Wed Mar 24, 2010 10:32 am
Posts: 7
Hello. I have been developing/maintaining an application over the last couple of years that runs in JBoss and uses JPA + Hibernate. I've observed the following in both JBoss 5.1.0 and 6.1.0 (Hibernate 3.3.1 & 3.6.6). Long ago I saw some weird behavior when constraint violations were encountered: some of the entity tables had rows inserted but others did not, even though I was within a transaction that was rolled back when the exception was caught. At the time my fix was to simply correct the constraint violation issues and the problem went away, even though the lack of transactional behavior was a bit disturbing.

Two years later I am revisiting this issue and have come across a troubling observation that explains the symptoms that I observed. It turns out that, even though I am within a transaction, my connection's autocommit flag is still true. I have verified this in several ways:
1) Step through the code. The moment I step over a call to EntityManager.flush() I can see modified data in a separate DB session (using pgAdmin)
2) Turn on SQL logging at the database (PostgreSQL 8.3 if it matters), no BEGIN/COMMIT/ROLLBACK ever appears
3) Add the following code before after my calls to EntityManager.persist/flush:

Code:
Session s = (Session)entityManager.getDelegate();
boolean autocommit = s.connection().getAutoCommit(); // always true


The way that I understand things, the proper behavior is that whenever I start a transaction autocommit should be disabled. I spent the better part of yesterday stepping through Hibernate/JBoss/Arjuna code and cannot find where this would ever happen. When grepping the Hibernate code, I find very few calls to Connection.setAutoCommit(false) and they appear in classes that wouldn't be used in my situation anyway (certain connection providers and transaction implementations). Based on that, I'm not sure that this post even belongs in the Hibernate forum (maybe the JBoss forum instead), but I have to start somewhere. Although grepping through the JBoss/Arjuna code, I don't see anywhere that it would happen either.

Here is the relevant persistence context definition and code that exhibits the autocommit behavior (note that I mentioned an entity that exists across several tables earlier, and this sample shows only 1 entity class, but both DAOs/PUs show the same symptoms):

Code:
    <persistence-unit name="georeo">
        <jta-data-source>java:/Georeo_DS</jta-data-source>
        <class>com.orci.websol.georeo.Georeo</class>
        <properties>
            <property name="hibernate.hbm2ddl.auto" value="validate" />
           
            <!-- this property wasn't here initially but adding it didn't help -->
            <property name="org.hibernate.transaction.manager_lookup_class"
               value="org.hibernate.transaction.JBossTransactionManagerLookup" />
        </properties>
    </persistence-unit>   


Code:
@PersistenceContext(unitName = "georeo")
private EntityManager entityManager;
@Resource
private UserTransaction utx;

public void updateGeoreos(String eventId,
      Map<Georeo, PersistableGeometry> georeosToGeoms) throws GeoreoException {
   try {
      utx.begin();

      for (Entry<Georeo, PersistableGeometry> entry : georeosToGeoms.entrySet()) {
         Georeo georeo = entry.getKey();
         PersistableGeometry geom = entry.getValue();
         entityManager.persist(georeo);
         // result of persist is visible to others immediately after this flush
         entityManager.flush();
         
         // insert the geometry
         String insert = createInsertStmt(georeo, geom);
         Query q = entityManager.createNativeQuery(insert);
         q.executeUpdate();
      }
      utx.commit();
   } catch (Exception e) {
      LOG.error("Could not update georeo for event " + eventId, e);
      try {
         utx.rollback();
      } catch (Exception ee) {
         LOG.warn("Failed to rollback", ee);
      }
      throw new GeoreoException("Could not update georeo for event " + eventId, e);
   }
}


From the code you can see that I am using JTA, so I don't/can't try to use EntityTransactions instead, and the code is using bean managed transactions (although it doesn't really need to be), but I have also tried container managed transactions with no luck. So my questions are
1) Am I correct in assuming that autocommit should be disabled when a transaction is started? (Cause otherwise it's not really a transaction, right?)
2) Who is responsible for disabling autocommit, Hibernate or the container?
3) Why isn't it being disabled? Am I missing a setting?

Thanks


Top
 Profile  
 
 Post subject: Re: Auto commit remains enabled in transaction
PostPosted: Mon Mar 26, 2012 5:53 pm 
Newbie

Joined: Wed Mar 24, 2010 10:32 am
Posts: 7
*bump* to push above all the spam from Friday


Top
 Profile  
 
 Post subject: Re: Auto commit remains enabled in transaction
PostPosted: Tue Mar 27, 2012 4:06 pm 
Newbie

Joined: Wed Mar 24, 2010 10:32 am
Posts: 7
Turned out to be a problem with the DataSource I was using (c3p0). Apparently to use CMTs in JBoss you must also use their DataSource implementation (defined in *-ds.xml). See https://community.jboss.org/thread/197395?tstart=0


Top
 Profile  
 
Display posts from previous:  Sort by  
Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 3 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.