{"record":{"id":"8c8ad5bf15b14b6f","repo":"alibaba/druid","slug":"connection-disabled","errorCode":null,"errorMessage":"connection disabled","messagePattern":"connection disabled","errorType":"exception","errorClass":"SQLException","httpStatus":null,"severity":"error","filePath":"core/src/main/java/com/alibaba/druid/pool/DruidPooledConnection.java","lineNumber":1184,"sourceCode":"                lock.unlock();\n            }\n        } else {\n            checkStateInternal();\n        }\n    }\n\n    private void checkStateInternal() throws SQLException {\n        if (closed) {\n            if (disableError != null) {\n                throw new SQLException(\"connection closed\", disableError);\n            } else {\n                throw new SQLException(\"connection closed\");\n            }\n        }\n\n        if (disable) {\n            if (disableError != null) {\n                throw new SQLException(\"connection disabled\", disableError);\n            } else {\n                throw new SQLException(\"connection disabled\");\n            }\n        }\n\n        if (holder == null) {\n            if (disableError != null) {\n                throw new SQLException(\"connection holder is null\", disableError);\n            } else {\n                throw new SQLException(\"connection holder is null\");\n            }\n        }\n    }\n\n    public String toString() {\n        if (conn != null) {\n            return conn.toString();\n        } else {","sourceCodeStart":1166,"sourceCodeEnd":1202,"githubUrl":"https://github.com/alibaba/druid/blob/fa8dc9912637a2f729eef9f55356621fec18d40e/core/src/main/java/com/alibaba/druid/pool/DruidPooledConnection.java#L1166-L1202","documentation":"Thrown by DruidPooledConnection.checkStateInternal() when the connection is disabled (disable flag true) AND a disableError is set. 'Disabled' means Druid has taken the connection out of use due to a detected problem but the chained disableError explains why — typically a fatal/validated error that did not also set closed.","triggerScenarios":"JDBC operation on a DruidPooledConnection whose disable flag is true and disableError != null; closed flag is false so it falls through to the disable branch at line 1183. The connection was disabled (e.g. by a validation failure or fatal error detected on the physical connection) but not yet closed.","commonSituations":"Connection failed keep-alive/validation and was disabled; a fatal error was detected and handleConnectionException disabled it; the pool's testWhileIdle marked the connection bad; using a connection after it was disabled but before/as it is being discarded.","solutions":["Inspect the chained disableError to find the underlying failure (validation query failed, fatal SQL state) and fix the DB/network side.","Discard the disabled connection reference and borrow a fresh one (try-with-resources ensures this).","Tune validation (validationQuery, testWhileIdle, testOnBorrow) so bad connections are detected and discarded before handout."],"exampleFix":"// before\nConnection c = dataSource.getConnection();\n// ... fatal error disables c ...\nc.createStatement(); // SQLException(\"connection disabled\", disableError)\n\n// after\ntry (Connection c = dataSource.getConnection()) {\n    use(c);\n} catch (SQLException e) {\n    // borrow a fresh connection on retry; the disabled one is gone\n}","handlingStrategy":"try-catch","validationCode":"if (pooledConn.isDisable()) {\n    Throwable why = pooledConn.getDisableError();\n    throw new IllegalStateException(\"connection disabled\" + (why == null ? \"\" : \": \" + why));\n}\n// proceed","typeGuard":"boolean usable = pooledConn != null && !pooledConn.isDisable() && !pooledConn.isClosed();","tryCatchPattern":"try {\n    pooledConn.createStatement();\n} catch (SQLException e) {\n    if (\"connection disabled\".equals(e.getMessage()) && e.getCause() != null) {\n        log.error(\"conn disabled by Druid due to: {}\", e.getCause());\n        borrowFreshAndRetry();\n    } else throw e;\n}","preventionTips":["Inspect the chained disableError to find the validation/fatal failure and fix the DB side.","Tune testWhileIdle / validationQuery so bad connections are discarded before handout.","Always borrow a fresh connection after a disabled one; never try to revive it."],"tags":["connection-disabled","validation","fatal-error","connection-pool","chained-cause"],"backgroundTag":null,"analyzedSha":"fa8dc9912637a2f729eef9f55356621fec18d40e","analyzedAt":"2026-08-14T04:55:06.789Z","schemaVersion":2},"datasetVersion":"2026-08-14T05:17:29.042Z"}