Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*
* Copyright (c) 2025 Contributors to the Eclipse Foundation.
* Copyright (c) 2025, 2026 Contributors to the Eclipse Foundation.
* Copyright (c) 1997, 2020 Oracle and/or its affiliates. All rights reserved.
*
* This program and the accompanying materials are made available under the
Expand Down Expand Up @@ -463,6 +463,15 @@ public Object getConnection(Subject sub, ConnectionRequestInfo cxReqInfo) throws
private void resetConnectionProperties(ManagedConnectionFactoryImpl managedConnectionFactoryImpl) throws ResourceException {
if (isClean) {

// cleanup() can be invoked on a ManagedConnection whose physical connection has
// already been torn down - for instance one marked for removal whose transaction
// has completed. In that case there is no connection to reset; resetIsolation()
// already tolerates a null connection, so guard resetAutoCommit() the same way to
// avoid a NullPointerException (see issue #24232).
if (getActualConnection() == null) {
return;
}

// If the ManagedConnection is clean, reset the transaction isolation level to
// what it was when it was when this ManagedConnection was cleaned up depending on
// the ConnectionRequestInfo passed.
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*
* Copyright (c) 2024 Contributors to the Eclipse Foundation.
* Copyright (c) 2024, 2026 Contributors to the Eclipse Foundation.
*
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License v. 2.0, which is available at
Expand Down Expand Up @@ -145,6 +145,32 @@ public void testAssociateAndDissociateConnection() throws Exception {
assertEquals(1, managedConnection1.connectionCount);
}

/**
* Reproduces issue #24232: cleanup() can be invoked on a pooled/XA ManagedConnection
* whose physical connection has already been torn down (e.g. a connection marked for
* removal whose transaction completed and which was then destroyed). In that state both
* actualConnection and pooledConnection are null, so resetConnectionProperties() must
* not dereference them. Before the fix this threw a NullPointerException from
* resetAutoCommit().
*/
@Test
public void testCleanupOnTornDownPooledConnectionDoesNotThrow() throws Exception {
ManagedConnectionImpl managedConnection = createManagedConnection(new MyPooledConnection(), null);
managedConnection.initializeConnectionType(ManagedConnectionImpl.ISPOOLEDCONNECTION);

// Application changed autoCommit (default is true), so resetConnectionProperties()
// would attempt to reset it on the - now absent - physical connection.
managedConnection.setLastAutoCommitValue(false);

// Tear the physical connection down: destroy() closes and nulls both the
// pooledConnection and the actualConnection for a pooled connection.
managedConnection.destroy();
assertNull(managedConnection.getActualConnection());

// cleanup() runs resetConnectionProperties() on the torn-down connection.
assertDoesNotThrow(managedConnection::cleanup);
}

/**
* Creates a ManagedConnectionImpl with a DSManagedConnectionFactory
*/
Expand Down
Loading