Issue Details (XML | Word | Printable)

Key: DBCP-3
Type: Bug Bug
Status: Closed Closed
Resolution: Fixed
Priority: Major Major
Assignee: Unassigned
Reporter: Adam Jenkins
Votes: 3
Watchers: 1
Operations

If you were logged in you would be able to see more operations.
Commons Dbcp

[dbcp] PoolableConnection.close() won't allow multiple close

Created: 16/Sep/03 03:16 AM   Updated: 25/Mar/08 08:11 AM
Return to search
Component/s: None
Affects Version/s: Nightly Builds
Fix Version/s: 1.3

Time Tracking:
Not Specified

Environment:
Operating System: All
Platform: All
Issue Links:
dependent
 

Bugzilla Id: 23185
Resolution Date: 18/Jul/07 06:48 AM


 Description  « Hide
Sun's javadoc for java.sql.Connection.close() specifies that calling close on an
already closed Connection is a no-op. However, PoolableConnection.close() (v
1.10) throws a SQLException if close() is called on a closed Connection.
PoolableConnection.close() should just return if the Connection is already
closed. Here is a patch:

To demonstrate the bug, just obtain an open PoolableConnection and call close()
on it twice; the second call will produce a SQLException. According to Sun's
spec, the second close() should just be a no-op. The current behaviour is
preferable to the old behaviour where it returned the Connection to the pool
twice, but it's still not according to the spec.

Here's a patch:

      • PoolableConnection.java.orig 2003-09-15 16:07:53.000000000 -0400
      • PoolableConnection.java 2003-09-15 16:08:11.000000000 -0400
        ***************
      • 108,114 ****
        */
        public synchronized void close() throws SQLException {
        if(isClosed()) { ! throw new SQLException("Already closed."); } else {
        try {
        _pool.returnObject(this);
      • 108,114 ----
        */
        public synchronized void close() throws SQLException {
        if(isClosed()) { ! return; } else {
        try {
        _pool.returnObject(this);


 All   Comments   Work Log   Change History   Subversion Commits      Sort Order: Ascending order - Click to sort in descending order
Dirk Verbeeck added a comment - 20/Sep/03 10:04 PM
I believe this behaviour is intended.
There is a junit test that fails if no exception is thrown:
testCantCloseConnectionTwice()

Also the alternative datasource implementation does the same in
org.apache.commons.dbcp.cpdsadapter.ConnectionImpl

I'm marking this issue WONTFIX until more evidence is presented that throwing an
exception is illegal / undesired.


Adam Jenkins added a comment - 22/Sep/03 10:19 AM
For evidence that Connection.close() shouldn't throw an exception just because the connection is already closed, see Sun's API spec for the Connction.close() method. http://java.sun.com/j2se/1.4.2/docs/api/java/sql/Connection.html#close() The relevent quote is: "Calling the method close on a Connection object that is already closed is a no-op." That makes it pretty clear to me that the PoolableConnection.close implementation is not what the spec intended in this regard. Note, I can well believe that the current behaviour was intended, and I think good arguments can be made for the spec's behaviour and for PoolableConnection's behaviour. However, I don't think there's any great advantage to either implementation, so I think the spec should win out. I found this problem because we actually had code which called close twice; once when the connection was done being used, and later in the finally block in case there was an error before the normal close. We were using DriverManager but recently decided to use connection pooling, and so switched to commons-dbcp and started getting exceptions. If I'd written the code, I wouldn't have called Connection.close twice anyway, but I can't really fault the original programmer since he was following Sun's spec, so I must fault the PoolableConnection implementation.

Mauro Botelho added a comment - 24/Sep/04 01:41 AM
This is a bug. According to
http://java.sun.com/j2se/1.4.2/docs/api/java/sql/Statement.html#close()

"Calling the method close on a Statement object that is already closed has no
effect."


Austin Mills added a comment - 28/Sep/04 04:41 AM
      • COM-1582 has been marked as a duplicate of this bug. ***

JZ added a comment - 18/Jan/05 11:42 PM
Note this is also related to 32441 - that one refers to the same problem with
PoolablePreparedStatements.

Ilja Preuß added a comment - 30/Aug/05 08:07 PM
Anyone working on this? This has been reported two years ago now, and it's
really a PITA when trying to introduce DBCP for a legacy app.

Jerome Lacoste added a comment - 25/Mar/06 03:08 AM
Can this be fixed? It's an obvious violation of the API contract and breaks
legacy applications. Thanks.

Sandy McArthur (from Bugzilla import) added a comment - 25/Mar/06 03:31 AM
(In reply to comment #7)
> Can this be fixed? It's an obvious violation of the API contract and breaks
> legacy applications. Thanks.

Yes, it needs to be fixed. Working on Dbcp is next on my personal todo list,
maybe someone else will get to it sooner.

In the existing code's defense the contract for close changed from Java 1.3 to 1.4:
http://java.sun.com/j2se/1.3/docs/api/java/sql/Connection.html#close()
http://java.sun.com/j2se/1.4.2/docs/api/java/sql/Connection.html#close()


Philippe Mouawad added a comment - 13/Jul/06 04:24 AM
See Comment of [Philippe Mouawad] 12/Jul/06 09:19 PM for a problem that occurs if this bug is not corrected.
http://issues.apache.org/jira/browse/DBCP-28

Philippe.


James Ring added a comment - 14/Jul/06 12:40 PM
Is there anything wrong with Adam Jenkin's patch that was posted nearly 3 years ago now?

Phil Steitz added a comment - 16/Jul/06 04:35 PM
This represents a behavior change that may break some existing code, so fix version is set to 1.3.

James Ring added a comment - 17/Jul/06 11:49 PM
Shouldn't we at least apply the patch to the trunk so that it appears in our nightlies?

Henri Yandell added a comment - 31/Oct/06 01:46 AM
Maybe time to branch 1.2.2 off and have trunk be 1.3?

Phil Steitz added a comment - 18/Jul/07 06:48 AM
Fixed in r 557176.