All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.ajjpj.asysmon.measure.jdbc.ASysMonConnection Maven / Gradle / Ivy

There is a newer version: 1.0-pre28
Show newest version
package com.ajjpj.asysmon.measure.jdbc;

import com.ajjpj.asysmon.ASysMonApi;
import com.ajjpj.asysmon.measure.ASimpleMeasurement;

import java.sql.*;
import java.util.Map;
import java.util.Properties;
import java.util.concurrent.Executor;

/**
 * @author arno
 */
public class ASysMonConnection implements Connection {
    private final Connection inner;
    private final ASysMonApi sysMon;

    private final String poolIdentifier;
    private volatile boolean isActive = false;
    private final AIConnectionCounter connectionCounter;

    public ASysMonConnection(Connection inner, ASysMonApi sysMon, String poolIdentifier, AIConnectionCounter connectionCounter) {
        this.inner = inner;
        this.sysMon = sysMon;
        this.poolIdentifier = poolIdentifier;
        this.connectionCounter = connectionCounter;

        connectionCounter.onOpenConnection(poolIdentifier);
    }

    private void makeActive() throws SQLException {
        if(getAutoCommit()) {
            // autocommit invalidates the underlying heuristics of 'active / passive', so we play it safe here
            makePassive();
            return;
        }

        if(!isActive) {
            connectionCounter.onActivateConnection(poolIdentifier);
            isActive = true;
        }
    }

    private void makePassive() {
        if(isActive) {
            connectionCounter.onPassivateConnection(poolIdentifier);
            isActive = false;
        }
    }

    private void onClose() throws SQLException {
        if(isActive) {
            connectionCounter.onPassivateConnection(poolIdentifier);
        }
        if(! isClosed()) {
            connectionCounter.onCloseConnection(poolIdentifier);
        }
    }

//------------------- Wrapper interface

    @Override public  T unwrap(Class iface) throws SQLException {
        makeActive();
        return inner.unwrap(iface); //TODO wrap this in a dynamic proxy to keep track of non-standard SQL stuff as well?
    }

    @Override public boolean isWrapperFor(Class iface) throws SQLException {
        return inner.isWrapperFor(iface);
    }

    //------------------- creating statements

    @Override public Statement createStatement() throws SQLException {
        makeActive();
        return wrap(inner.createStatement());
    }

    @Override public PreparedStatement prepareStatement(String sql) throws SQLException {
        makeActive();
        return wrap(inner.prepareStatement(sql), sql);
    }

    @Override public CallableStatement prepareCall(String sql) throws SQLException {
        makeActive();
        return wrap(inner.prepareCall(sql), sql);
    }

    @Override public Statement createStatement(int resultSetType, int resultSetConcurrency) throws SQLException {
        makeActive();
        return wrap(inner.createStatement(resultSetType, resultSetConcurrency));
    }

    @Override public PreparedStatement prepareStatement(String sql, int resultSetType, int resultSetConcurrency) throws SQLException {
        makeActive();
        return wrap(inner.prepareStatement(sql, resultSetType, resultSetConcurrency), sql);
    }

    @Override public CallableStatement prepareCall(String sql, int resultSetType, int resultSetConcurrency) throws SQLException {
        makeActive();
        return wrap(inner.prepareCall(sql, resultSetType, resultSetConcurrency), sql);
    }

    @Override public Statement createStatement(int resultSetType, int resultSetConcurrency, int resultSetHoldability) throws SQLException {
        makeActive();
        return wrap(inner.createStatement(resultSetType, resultSetConcurrency, resultSetHoldability));
    }

    @Override public PreparedStatement prepareStatement(String sql, int resultSetType, int resultSetConcurrency, int resultSetHoldability) throws SQLException {
        makeActive();
        return wrap(inner.prepareStatement(sql, resultSetType, resultSetConcurrency, resultSetHoldability), sql);
    }

    @Override public CallableStatement prepareCall(String sql, int resultSetType, int resultSetConcurrency, int resultSetHoldability) throws SQLException {
        makeActive();
        return wrap(inner.prepareCall(sql, resultSetType, resultSetConcurrency, resultSetHoldability), sql);
    }

    @Override public PreparedStatement prepareStatement(String sql, int autoGeneratedKeys) throws SQLException {
        makeActive();
        return wrap(inner.prepareStatement(sql, autoGeneratedKeys), sql);
    }

    @Override public PreparedStatement prepareStatement(String sql, int[] columnIndexes) throws SQLException {
        makeActive();
        return wrap(inner.prepareStatement(sql, columnIndexes), sql);
    }

    @Override public PreparedStatement prepareStatement(String sql, String[] columnNames) throws SQLException {
        makeActive();
        return wrap(inner.prepareStatement(sql, columnNames), sql);
    }

    private Statement wrap(Statement stmt) throws SQLException {
        makeActive();
        return new ASysMonStatement(this, stmt, sysMon);
    }

    private PreparedStatement wrap(PreparedStatement stmt, String sql) throws SQLException {
        makeActive();
        return new ASysMonPreparedStatement(this, stmt, sysMon, sql);
    }

    private CallableStatement wrap(CallableStatement stmt, String sql) throws SQLException {
        makeActive();
        return new ASysMonCallableStatement(this, stmt, sysMon, sql);
    }

    //------------------------------- transaction handling

    @Override
    public void commit() throws SQLException {
        makePassive();
        final ASimpleMeasurement m = sysMon.start(ASysMonStatement.IDENT_PREFIX_JDBC + "commit");
        try {
            inner.commit();
        }
        finally {
            m.finish();
        }
    }

    @Override
    public void rollback() throws SQLException {
        makePassive();
        final ASimpleMeasurement m = sysMon.start(ASysMonStatement.IDENT_PREFIX_JDBC + "rollback");
        try {
            inner.rollback();
        } finally {
            m.finish();
        }
    }

    @Override
    public Savepoint setSavepoint() throws SQLException {
        final ASimpleMeasurement m = sysMon.start(ASysMonStatement.IDENT_PREFIX_JDBC + "setSavepoint");
        try {
            return inner.setSavepoint();
        } finally {
            m.finish();
        }
    }

    @Override
    public Savepoint setSavepoint(String name) throws SQLException {
        final ASimpleMeasurement m = sysMon.start(ASysMonStatement.IDENT_PREFIX_JDBC + "setSavepoint");
        try {
            return inner.setSavepoint(name);
        } finally {
            m.finish();
        }
    }

    @Override
    public void rollback(Savepoint savepoint) throws SQLException {
        final ASimpleMeasurement m = sysMon.start(ASysMonStatement.IDENT_PREFIX_JDBC + "rollback");
        try {
            inner.rollback(savepoint);
        } finally {
            m.finish();
        }
    }

    @Override
    public void releaseSavepoint(Savepoint savepoint) throws SQLException {
        final ASimpleMeasurement m = sysMon.start(ASysMonStatement.IDENT_PREFIX_JDBC + "releaseSavepoint");
        try {
            inner.releaseSavepoint(savepoint);
        } finally {
            m.finish();
        }
    }

    //------------------- misc / ignored by ASysMon

    @Override
    public void close() throws SQLException {
        onClose();
        inner.close();
    }


    @Override
    public String nativeSQL(String sql) throws SQLException {
        makeActive();
        return inner.nativeSQL(sql);
    }

    @Override
    public void setAutoCommit(boolean autoCommit) throws SQLException {
        makeActive();
        inner.setAutoCommit(autoCommit);
    }

    @Override
    public boolean getAutoCommit() throws SQLException {
        return inner.getAutoCommit();
    }

    @Override
    public boolean isClosed() throws SQLException {
        return inner.isClosed();
    }

    @Override
    public DatabaseMetaData getMetaData() throws SQLException {
        makeActive();
        return inner.getMetaData();
    }

    @Override
    public void setReadOnly(boolean readOnly) throws SQLException {
        makeActive();
        inner.setReadOnly(readOnly);
    }

    @Override
    public boolean isReadOnly() throws SQLException {
        makeActive();
        return inner.isReadOnly();
    }

    @Override
    public void setCatalog(String catalog) throws SQLException {
        makeActive();
        inner.setCatalog(catalog);
    }

    @Override
    public String getCatalog() throws SQLException {
        makeActive();
        return inner.getCatalog();
    }

    @Override
    public void setTransactionIsolation(int level) throws SQLException {
        makeActive();
        inner.setTransactionIsolation(level);
    }

    @Override
    public int getTransactionIsolation() throws SQLException {
        makeActive();
        return inner.getTransactionIsolation();
    }

    @Override
    public SQLWarning getWarnings() throws SQLException {
        makeActive();
        return inner.getWarnings();
    }

    @Override
    public void clearWarnings() throws SQLException {
        makeActive();
        inner.clearWarnings();
    }

    @Override
    public Map> getTypeMap() throws SQLException {
        makeActive();
        return inner.getTypeMap();
    }

    @Override
    public void setTypeMap(Map> map) throws SQLException {
        makeActive();
        inner.setTypeMap(map);
    }

    @Override
    public void setHoldability(int holdability) throws SQLException {
        makeActive();
        inner.setHoldability(holdability);
    }

    @Override
    public int getHoldability() throws SQLException {
        makeActive();
        return inner.getHoldability();
    }

    @Override
    public Clob createClob() throws SQLException {
        makeActive();
        return inner.createClob();
    }

    @Override
    public Blob createBlob() throws SQLException {
        makeActive();
        return inner.createBlob();
    }

    @Override
    public NClob createNClob() throws SQLException {
        makeActive();
        return inner.createNClob();
    }

    @Override
    public SQLXML createSQLXML() throws SQLException {
        makeActive();
        return inner.createSQLXML();
    }

    @Override
    public boolean isValid(int timeout) throws SQLException {
        makeActive();
        return inner.isValid(timeout);
    }

    @Override
    public void setClientInfo(String name, String value) throws SQLClientInfoException {
        inner.setClientInfo(name, value);
    }

    @Override
    public void setClientInfo(Properties properties) throws SQLClientInfoException {
        inner.setClientInfo(properties);
    }

    @Override
    public String getClientInfo(String name) throws SQLException {
        makeActive();
        return inner.getClientInfo(name);
    }

    @Override
    public Properties getClientInfo() throws SQLException {
        makeActive();
        return inner.getClientInfo();
    }

    @Override
    public Array createArrayOf(String typeName, Object[] elements) throws SQLException {
        makeActive();
        return inner.createArrayOf(typeName, elements);
    }

    @Override
    public Struct createStruct(String typeName, Object[] attributes) throws SQLException {
        makeActive();
        return inner.createStruct(typeName, attributes);
    }

    // introduced with JDK 1.7

    public void setSchema(String schema) throws SQLException {
        makeActive();
        inner.setSchema(schema);
    }

    public String getSchema() throws SQLException {
        makeActive();
        return inner.getSchema();
    }

    public void abort(Executor executor) throws SQLException {
        makeActive();
        inner.abort(executor);
    }

    public void setNetworkTimeout(Executor executor, int milliseconds) throws SQLException {
        makeActive();
        inner.setNetworkTimeout(executor, milliseconds);
    }

    public int getNetworkTimeout() throws SQLException {
        makeActive();
        return inner.getNetworkTimeout();
    }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy