Transaction problems in asynchronous methods
ibenjes Oct 2, 2012 11:49 AMHi,
I have a strange behaviour with Seam 2.2, JBoss 5.1 and asynchronous methods (using quartz).
I've got a pool of 10 async threads for various tasks. They normally work fine, performing db queries and updates etc.
If there is an exception in one async method it doesn't impact the next async method called from the same thread.
But I now have one case where I get this exception in one particular thread:
012-10-02 05:45:26,743 WARN [][JDBCExceptionReporter] (er-4) SQL Error: 0, SQLState: null
2012-10-02 05:45:26,743 ERROR [][JDBCExceptionReporter] (er-4) Transaction is not active: tx=TransactionImple < ac, BasicAction: 7f000001:b824:5069f752:15d status: ActionStatus.ABORT_ONLY >; - nested throwable: (javax.resource.ResourceException: Transaction is not active: tx=TransactionImple < ac, BasicAction: 7f000001:b824:5069f752:15d status: ActionStatus.ABORT_ONLY >)
2012-10-02 05:45:26,743 INFO [][DefaultLoadEventListener] (er-4) Error performing load command
org.hibernate.exception.GenericJDBCException: Cannot open connection
at org.hibernate.exception.SQLStateConverter.handledNonSpecificException(SQLStateConverter.java:126)
at org.hibernate.exception.SQLStateConverter.convert(SQLStateConverter.java:114)
at org.hibernate.exception.JDBCExceptionHelper.convert(JDBCExceptionHelper.java:66)
at org.hibernate.exception.JDBCExceptionHelper.convert(JDBCExceptionHelper.java:52)
at org.hibernate.jdbc.ConnectionManager.openConnection(ConnectionManager.java:449)
at org.hibernate.jdbc.ConnectionManager.getConnection(ConnectionManager.java:167)
at org.hibernate.jdbc.AbstractBatcher.prepareQueryStatement(AbstractBatcher.java:161)
at org.hibernate.loader.Loader.prepareQueryStatement(Loader.java:1573)
After this every time this thread (er-4) is used and a query is executed I get the same exception.
How can I recover from this and why is this?
The method that causes the exception is an Observer for asyncronous events:
@Observer(value="asyncEvent.user.TablePrefChanged.prefs",create=true)
@Transactional
public void updateTablePref(Long tabId,String state){
UserTablePrefs pref = entityManager.find(UserTablePrefs.class,tabId);
...
}
I am validating the db connection before a connection is used form the pool (from the deployment descriptor):
<!--pooling parameters-->
<min-pool-size>5</min-pool-size>
<max-pool-size>100</max-pool-size>
<blocking-timeout-millis>5000</blocking-timeout-millis>
<idle-timeout-minutes>15</idle-timeout-minutes>
<prepared-statement-cache-size>50</prepared-statement-cache-size>
<check-valid-connection-sql>select 1 from dual</check-valid-connection-sql>