package org.postgresql.jdbc3;

import java.sql.PreparedStatement;
import java.sql.SQLException;
import java.util.Properties;



public class CacheConnection extends Jdbc3Connection
{

    StatementPool statementPool=null;
    
    public CacheConnection(String host, int port, String user, String database, Properties info, String url) throws SQLException
    {
        super(host, port, user, database, info, url);
        statementPool = new StatementPool(this);
        
    }
    
    public PreparedStatement prepareStatement(String sql) throws SQLException
    {
        PStmtKey stmtKey = new PStmtKey( sql );
        return  (PreparedStatement)statementPool.getStatement( stmtKey );    
    }
    

    public PreparedStatement prepareStatement(String sql, int resultSetType, int resultSetConcurrency )
            throws SQLException
    {
        PStmtKey stmtKey = new PStmtKey( sql,resultSetType, resultSetConcurrency );
        return  (PreparedStatement)statementPool.getStatement( stmtKey );    
    }

    
    
    public PreparedStatement prepareStatement(String sql, int resultSetType, int resultSetConcurrency ,
            int resultSetHoldability) throws SQLException
    {
        PStmtKey stmtKey = new PStmtKey( sql, resultSetType, resultSetConcurrency, resultSetHoldability );
        return  (PreparedStatement)statementPool.getStatement( stmtKey );    
    }

    public void close()
    {
        try
        {
            statementPool.close();
        }
        catch( SQLException ex )
        {}
        
        super.close();
    }
    /**
     * A key uniquely identifying {*link PreparedStatement}s.
     * 
     * borrowed directly from apache dbcp
     */
    
    class PStmtKey 
    {
        protected String _sql = null;
        protected Integer _resultSetType = null;
        protected Integer _resultSetConcurrency = null;
        protected Integer _resultSetHoldability = null;

        PStmtKey(String sql) 
        {
            
            _sql = sql.trim();
        }

        PStmtKey(String sql, int resultSetType, int resultSetConcurrency) 
        {
            _sql = sql.trim();
            _resultSetType = new Integer(resultSetType);
            _resultSetConcurrency = new Integer(resultSetConcurrency);
        }

        PStmtKey(String sql, int resultSetType, int resultSetConcurrency, int resultSetHoldability ) 
        {
            _sql = sql.trim();
            _resultSetType = new Integer(resultSetType);
            _resultSetConcurrency = new Integer(resultSetConcurrency);
            _resultSetHoldability = new Integer(resultSetHoldability);
        }
        public boolean equals(Object that) 
        {
            try 
            {
                PStmtKey key = (PStmtKey) that;
                return(((null == _sql && null == key._sql) || _sql.equals(key._sql)) &&
                       ((null == _resultSetType && null == key._resultSetType) || _resultSetType.equals(key._resultSetType)) &&
                       ((null == _resultSetConcurrency && null == key._resultSetConcurrency) || _resultSetConcurrency.equals(key._resultSetConcurrency)) &&
                       ((null == _resultSetHoldability && null == key._resultSetHoldability) || _resultSetHoldability.equals(key._resultSetHoldability))
                      );
            } catch (ClassCastException e) 
            {
                return false;
            } catch (NullPointerException e) 
            {
                return false;
            }
        }

        public int hashCode() 
        {
            return(null == _sql ? 0 : _sql.hashCode());
        }

        public String toString() 
        {
            StringBuffer buf = new StringBuffer();
            buf.append("PStmtKey: sql=");
            buf.append(_sql);
            buf.append(", resultSetType=");
            buf.append(_resultSetType);
            buf.append(", resultSetConcurrency=");
            buf.append(_resultSetConcurrency);
            buf.append(", resultHoldability=" );
            buf.append(_resultSetHoldability);
            return buf.toString();
        }
    }

   
}
