1 Reply Latest reply on Mar 8, 2006 7:40 PM by achitre

    Batching, Hibernate Stateless Session & JBoss...

    achitre

      Hello,

      We have a piece of code that works flawlessly under Weblogic 8.1, but doesn't work under JBoss 4.0. This code performs batch update using 'BatchingBatcher' class in Hibernate and uses 'Hibernate Stateless session'. Under JBoss we get the following exception:

      Caused by: java.sql.SQLException: Closed Statement
       at oracle.jdbc.driver.DatabaseError.throwSqlException(DatabaseError.java:112)
       at oracle.jdbc.driver.DatabaseError.throwSqlException(DatabaseError.java:146)
       at oracle.jdbc.driver.DatabaseError.throwSqlException(DatabaseError.java:208)
       at oracle.jdbc.driver.OracleStatement.ensureOpen(OracleStatement.java:3523)
       at oracle.jdbc.driver.OraclePreparedStatement.executeBatch(OraclePreparedStatement.java:10538)
       at org.jboss.resource.adapter.jdbc.WrappedStatement.executeBatch(WrappedStatement.java:487)
       at org.hibernate.jdbc.BatchingBatcher.doExecuteBatch(BatchingBatcher.java:58)
       at org.hibernate.jdbc.BatchingBatcher.addToBatch(BatchingBatcher.java:34)
       at org.hibernate.persister.entity.AbstractEntityPersister.insert(AbstractEntityPersister.java:2062)
      
      
      
      
      While debugging I noticed that the 'batchUpdate' instance variable in AbstractBatcher *automagically* gets cleared during the update process. Under JBoss, this is of the type 'WrappedStatement'.

      Is there some kinda timeout that's getting triggered under JBoss? Our transaction timeout is set to 3600.

      Any help will be greatly appreciated.

        • 1. Re: Batching, Hibernate Stateless Session & JBoss...
          achitre

          Turns out that this is not really a JBoss issue, but a Hibernate issue. It looks like the 'AbstractBatcher' class in Hibernate is not quite set up correctly to handle batch updates. We changed the following method in this class to fix this issue:

          public boolean hasOpenResources() {
          
           //return resultSetsToClose.size() > 0 || statementsToClose.size() > 0;
           return resultSetsToClose.size() > 0 || statementsToClose.size() > 0 || (batchUpdate != null);
           }
          


          When a connection is closed, this method is used to check if there are any open resources. In batch update mode, Hibernate doesn't use the 'resultSetsToClose' & 'statementsToClose' variables; but uses the 'batchUpdate' variable. As such, this method needs to return 'true' if batch update is in process.

          As for, why this worked in Weblogic and not in JBoss, my only explanation is that JBoss does a better job of cleaning resources after the connection is closed than Weblogic does.

          It seems like, when a connection is closed, JBoss closes all the associated PreparedStatements; but Weblogic keeps them open. In this particular case, it seems like, Weblogic was re-attaching a connection to the old PreparedStatement.

          Hope this all makes sense. In any case, I will post this reply to the Hibernate mailing list; but I thought I should let everyone know that this isn't a JBoss issue.