I’m currently using Dropwizard + Jooq and Tomcat jdbc for the connection pool.
I’m seeing issues when a connection dies it’s not evicted from the connection
pool until the validator runs. While I can turn the rate up at which the
validator runs its seems odd that a closed connection is returned to the pool.
Example error: (repeats with different queries many times before the connection
is killed)
....user`.`login` WHERE `session`.`id` = ?]; No operations allowed after
connection closed.
....
at org.jooq_3.9.1.MYSQL.debug(Unknown Source) ... Caused by:
com.mysql.jdbc.exceptions.jdbc4.MySQLNonTransientConnectionException: No
operations allowed after connection closed. ... Caused by:
com.mysql.jdbc.exceptions.jdbc4.CommunicationsException: Communications link
failure The last packet successfully received from the server was 11,618
milliseconds ago. The last packet sent successfully to the server was 5,005
milliseconds ago. ... 1 common frames omitted Caused by:
java.net.SocketTimeoutException: Read timed out ... 28 common frames omitted
I’m able to fix this by getting a reference to the connection and manually
setting it to discarded, but his is quite hackey.
ConnectionListener extends DefaultExecuteListener {
...
public ConnectionListener() {}
@Override
public void exception(ExecuteContext ctx) {
try {
if (ctx != null && ctx.exception() != null) {
//Proceed to check if we recieved a DataAccessException
if (ctx.exception() instanceof DataAccessException) {
DataAccessException exception = (DataAccessException)
ctx.exception();
//If the error is network related discard the connection
if (isNetworkError(exception)) {
//The underlying ProxyConnection which we need to call
setDiscarded is a few levels deep
Connection conn = ctx.connection();
DefaultConnection dConn = (DefaultConnection) conn;
SettingsEnabledConnection sConn =
(SettingsEnabledConnection) dConn;
ProviderEnabledConnection pConn =
(ProviderEnabledConnection) sConn.getDelegate();
//Get the Proxy connection handler
InvocationHandler handler =
Proxy.getInvocationHandler(pConn.getDelegate());
//Get the Proxy connection
ProxyConnection proxyConnection = (ProxyConnection)
((DisposableConnectionFacade)
handler).getNext();
//Discard the connection
proxyConnection.getConnection().setDiscarded(true);
}
}
}
} catch (Exception e) {
logger.error("ConnectionListener caught unexpected error", e);
}
}