Hello jbpm gurus,
We're seeing database connection leakage with jBPM 3.2.3 in our unit tests.
Specifically, this JUnit test fails, showing that connections are not
being released back to the connection pool:
int connectionsBorrowed = datasource.getBorrowedConnectionsCount();
// getBorrowedConnectionsCount() is a method on
Oracle's UCP connection pooling
JbpmConfiguration config =
JbpmConfiguration.parseResource("jbpm.cfg.xml");
JbpmContext context = config.createJbpmContext();
context.getSession();
assertEquals(connectionsBorrowed + 1,
datasource.getBorrowedConnectionsCount()); // passes
context.close();
assertEquals("db connection leakage", connectionsBorrowed, datasource
.getBorrowedConnectionsCount()); // fails
Here's the snippet of our jbpm.cfg.xml file that configures the
persistence service for our test cases:
<service name="persistence">
<factory>
<bean class="org.jbpm.persistence.db.DbPersistenceServiceFactory">
<field name="dataSourceJndiName"><string
value="jdbc/bpsmDS"/> </field>
<field name="isCurrentSessionEnabled"><false /></field>
<field name="isTransactionEnabled"><true /></field>
</bean>
</factory>
</service>
The issue might be related to the DbPersistenceService methods
getConnection(boolean) and getSession(). getConnection(boolean)
initially sets mustConnectionBeClosed to true when we get a connection
out of the datasource, but getSession() then sets this flag back to
false.
As a workaround, we wrote the following custom method for closing a
JbpmContext):
public void close(JbpmContext context) {
Connection connection = context.getConnection();
context.close();
try {
connection.close(); // release connection back to pool
} catch (SQLException e) {
throw new IllegalStateException(e);
}
}
In our non-test environment (where we use JTA transactions), we are
not experiencing connection leakage, so my guess is that the container
(WebSphere) has been closing the connection automatically at the end
of the transaction.
Questions:
1. Have we misconfigured jBPM or is there some other reason why we're
leaking database connections in our test environment?
2. Is it ok if we start explicitly calling connection.close() in the
container? For example, will doing so prevent the container from
committing it's transaction (I'm guessing not)? So far our testing
shows no problems whether or not we explicitly call close() in a JTA
environment, but I wanted to make sure about this....
Looking forward to your thoughts on the above questions,
Brian Westrich
bw(a)mcwest.com