{"record":{"id":"e7413d269ed2bfd4","repo":"hibernate/hibernate-orm","slug":"cannot-reconnect-to-a-new-user-supplied-connection","errorCode":null,"errorMessage":"Cannot reconnect to a new user-supplied connection because currently connected; must disconnect before reconnecting.","messagePattern":"Cannot reconnect to a new user-supplied connection because currently connected; must disconnect before reconnecting\\.","errorType":"exception","errorClass":"IllegalArgumentException","httpStatus":null,"severity":"error","filePath":"hibernate-core/src/main/java/org/hibernate/resource/jdbc/internal/LogicalConnectionProvidedImpl.java","lineNumber":125,"sourceCode":"\t\t\treturn providedConnection;\n\t\t}\n\t\tfinally {\n\t\t\tprovidedConnection = null;\n\t\t}\n\t}\n\n\t@Override\n\tpublic void manualReconnect(@Nonnull Connection connection) {\n\t\terrorIfClosed();\n\t\tif ( connection == null ) {\n\t\t\tthrow new IllegalArgumentException( \"cannot reconnect using a null connection\" );\n\t\t}\n\t\telse if ( connection == providedConnection ) {\n\t\t\t// likely an unmatched reconnect call (no matching disconnect call)\n\t\t\tCONNECTION_LOGGER.reconnectingSameConnectionAlreadyConnected();\n\t\t}\n\t\telse if ( providedConnection != null ) {\n\t\t\tthrow new IllegalArgumentException(\n\t\t\t\t\t\"Cannot reconnect to a new user-supplied connection because currently connected; must disconnect before reconnecting.\"\n\t\t\t);\n\t\t}\n\t\tprovidedConnection = connection;\n\t\tCONNECTION_LOGGER.manuallyReconnectedLogicalConnection();\n\t}\n\n\t@Override\n\tprotected Connection getConnectionForTransactionManagement() {\n\t\treturn providedConnection;\n\t}\n\n\t@Override\n\tprotected void afterCompletion() {\n\t\tafterTransaction();\n\t\tresetConnection( initiallyAutoCommit );\n\t}\n","sourceCodeStart":107,"sourceCodeEnd":143,"githubUrl":"https://github.com/hibernate/hibernate-orm/blob/fad1729dce015f908198d57a8d80274a30f905a5/hibernate-core/src/main/java/org/hibernate/resource/jdbc/internal/LogicalConnectionProvidedImpl.java#L107-L143","documentation":"IllegalArgumentException from LogicalConnectionProvidedImpl.manualReconnect(): reconnect was called with a DIFFERENT Connection while the session still holds its original user-supplied connection (providedConnection != null). A session swaps connections only through the disconnect/reconnect pair; reconnecting the very same connection is tolerated (just logged), but a new one while connected is rejected.","triggerScenarios":"session.reconnect(newConnection) without a prior session.disconnect(); calling reconnect twice with different connections per request; swapping connections for routing/tenancy by reconnect while connected.","commonSituations":"Per-request code that reconnects unconditionally; error paths that skip disconnect; legacy multi-tenant hacks that try to point a live session at another database.","solutions":["Always pair reconnect with a prior disconnect: if (session.isConnected()) session.disconnect();","Only reconnect when the session is actually disconnected — guard the call","For multi-tenant routing use Hibernate multi-tenancy or distinct sessions per tenant, not connection swapping"],"exampleFix":"// before\nsession.reconnect(requestConnection); // throws: still holding previous connection\n\n// after\nif (session.isConnected()) session.disconnect();\nsession.reconnect(requestConnection);","handlingStrategy":"validation","validationCode":"// swap connections only through the disconnect -> reconnect pair\nif (session.isConnected()) {\n  session.disconnect();\n}\nsession.reconnect(requestConnection);","typeGuard":"static boolean canAcceptNewConnection(org.hibernate.Session s) {\n  return s != null && s.isOpen() && !s.isConnected();\n}","tryCatchPattern":"catch (IllegalArgumentException e) {\n  // reconnect was rejected because the session still holds a connection:\n  // disconnect() first, then retry reconnect with the new connection\n}","preventionTips":["Treat disconnect/reconnect as an atomic pair around any connection swap","Reconnect only when isConnected() is false","Use distinct sessions per tenant/database instead of live connection swapping"],"tags":["hibernate","session","api-misuse","connection-management"],"backgroundTag":"invalid-session-state","analyzedSha":"fad1729dce015f908198d57a8d80274a30f905a5","analyzedAt":"2026-08-22T04:13:57.527Z","schemaVersion":2},"datasetVersion":"2026-08-22T09:17:25.309Z"}