コード例 #1
0
 /**
  * This will be called if the Connection returned by the getConnection method came from a
  * PooledConnection, and the user calls the close() method of this connection object. What we need
  * to do here is to release this PooledConnection from our pool...
  */
 @Override
 public void connectionClosed(ConnectionEvent event) {
   PooledConnection pc = (PooledConnection) event.getSource();
   // if this event occurred because we were validating, or if this
   // connection has been marked for removal, ignore it
   // otherwise return the connection to the pool.
   if (!validatingSet.contains(pc)) {
     PooledConnectionAndInfo pci = pcMap.get(pc);
     if (pci == null) {
       throw new IllegalStateException(NO_KEY_MESSAGE);
     }
     try {
       _pool.returnObject(pci.getUserPassKey(), pci);
     } catch (Exception e) {
       System.err.println("CLOSING DOWN CONNECTION AS IT COULD " + "NOT BE RETURNED TO THE POOL");
       pc.removeConnectionEventListener(this);
       try {
         _pool.invalidateObject(pci.getUserPassKey(), pci);
       } catch (Exception e3) {
         System.err.println("EXCEPTION WHILE DESTROYING OBJECT " + pci);
         e3.printStackTrace();
       }
     }
   }
 }
コード例 #2
0
  /**
   * If a fatal error occurs, close the underlying physical connection so as not to be returned in
   * the future
   */
  public void connectionErrorOccurred(ConnectionEvent event) {
    PooledConnection pc = (PooledConnection) event.getSource();
    if (cleanupMap.containsKey(pc)) {
      return; // waiting for listener cleanup - ignore event
    }
    try {
      if (null != event.getSQLException()) {
        System.err.println(
            "CLOSING DOWN CONNECTION DUE TO INTERNAL ERROR (" + event.getSQLException() + ")");
      }
      cleanupMap.put(pc, null); // mark for cleanup
      muteMap.put(pc, null); // ignore events until listener is removed
    } catch (Exception ignore) {
      // ignore
    }

    PooledConnectionAndInfo info = (PooledConnectionAndInfo) pcMap.get(pc);
    if (info == null) {
      throw new IllegalStateException(NO_KEY_MESSAGE);
    }
    try {
      _pool.invalidateObject(info.getUserPassKey(), info);
    } catch (Exception e) {
      System.err.println("EXCEPTION WHILE DESTROYING OBJECT " + info);
      e.printStackTrace();
    }
  }
コード例 #3
0
 /**
  * This will be called if the Connection returned by the getConnection method came from a
  * PooledConnection, and the user calls the close() method of this connection object. What we need
  * to do here is to release this PooledConnection from our pool...
  */
 public void connectionClosed(ConnectionEvent event) {
   PooledConnection pc = (PooledConnection) event.getSource();
   // if this event occurred because we were validating, or if this
   // connection has been marked for removal, ignore it
   // otherwise return the connection to the pool.
   if (!muteMap.containsKey(pc)) {
     PooledConnectionAndInfo info = (PooledConnectionAndInfo) pcMap.get(pc);
     if (info == null) {
       throw new IllegalStateException(NO_KEY_MESSAGE);
     }
     try {
       _pool.returnObject(info.getUserPassKey(), info);
     } catch (Exception e) {
       System.err.println("CLOSING DOWN CONNECTION AS IT COULD " + "NOT BE RETURNED TO THE POOL");
       cleanupMap.put(pc, null); // mark for cleanup
       muteMap.put(pc, null); // ignore events until listener is removed
       try {
         _pool.invalidateObject(info.getUserPassKey(), info);
       } catch (Exception e3) {
         System.err.println("EXCEPTION WHILE DESTROYING OBJECT " + info);
         e3.printStackTrace();
       }
     }
   }
 }
コード例 #4
0
 /**
  * Invalidates the PooledConnection in the pool. The KeyedCPDSConnectionFactory closes the
  * connection and pool counters are updated appropriately. Also clears any idle instances
  * associated with the username that was used to create the PooledConnection. Connections
  * associated with this user are not affected and they will not be automatically closed on return
  * to the pool.
  */
 @Override
 public void invalidate(PooledConnection pc) throws SQLException {
   PooledConnectionAndInfo info = pcMap.get(pc);
   if (info == null) {
     throw new IllegalStateException(NO_KEY_MESSAGE);
   }
   UserPassKey key = info.getUserPassKey();
   try {
     _pool.invalidateObject(key, info); // Destroy and update pool counters
     _pool.clear(key); // Remove any idle instances with this key
   } catch (Exception ex) {
     throw new SQLException("Error invalidating connection", ex);
   }
 }
コード例 #5
0
  /**
   * If a fatal error occurs, close the underlying physical connection so as not to be returned in
   * the future
   */
  @Override
  public void connectionErrorOccurred(ConnectionEvent event) {
    PooledConnection pc = (PooledConnection) event.getSource();
    if (null != event.getSQLException()) {
      System.err.println(
          "CLOSING DOWN CONNECTION DUE TO INTERNAL ERROR (" + event.getSQLException() + ")");
    }
    pc.removeConnectionEventListener(this);

    PooledConnectionAndInfo info = pcMap.get(pc);
    if (info == null) {
      throw new IllegalStateException(NO_KEY_MESSAGE);
    }
    try {
      _pool.invalidateObject(info.getUserPassKey(), info);
    } catch (Exception e) {
      System.err.println("EXCEPTION WHILE DESTROYING OBJECT " + info);
      e.printStackTrace();
    }
  }
コード例 #6
0
 private void closeDueToException(PooledConnectionAndInfo info) {
   if (info != null) {
     try {
       info.getPooledConnection().getConnection().close();
     } catch (Exception e) {
       // do not throw this exception because we are in the middle
       // of handling another exception.  But record it because
       // it potentially leaks connections from the pool.
       getLogWriter()
           .println(
               "[ERROR] Could not return connection to "
                   + "pool during exception handling. "
                   + e.getMessage());
     }
   }
 }
コード例 #7
0
  /** Attempt to establish a database connection. */
  public synchronized Connection getConnection(String username, String password)
      throws SQLException {
    if (isNew) {
      throw new SQLException(
          "Must set the ConnectionPoolDataSource "
              + "through setDataSourceName or setConnectionPoolDataSource"
              + " before calling getConnection.");
    }

    getConnectionCalled = true;
    Map pools = (Map) dsInstanceMap.get(instanceKey);
    PoolKey key = getPoolKey(username);
    Object pool = pools.get(key);
    if (pool == null) {
      try {
        registerPool(username, password);
        pool = pools.get(key);
      } catch (Exception e) {
        e.printStackTrace();
        throw new SQLException(e.getMessage());
      }
    }

    PooledConnectionAndInfo info = null;
    if (pool instanceof ObjectPool) {
      try {
        info = (PooledConnectionAndInfo) ((ObjectPool) pool).borrowObject();
      } catch (NoSuchElementException e) {
        closeDueToException(info);
        throw new SQLException(e.getMessage());
      } catch (RuntimeException e) {
        closeDueToException(info);
        throw e;
      } catch (SQLException e) {
        closeDueToException(info);
        throw e;
      } catch (Exception e) {
        closeDueToException(info);
        throw new SQLException(e.getMessage());
      }
    } else {
      // assume KeyedObjectPool
      try {
        UserPassKey upkey = getUserPassKey(username, password);
        info = (PooledConnectionAndInfo) ((KeyedObjectPool) pool).borrowObject(upkey);
      } catch (NoSuchElementException e) {
        closeDueToException(info);
        throw new SQLException(e.getMessage());
      } catch (RuntimeException e) {
        closeDueToException(info);
        throw e;
      } catch (SQLException e) {
        closeDueToException(info);
        throw e;
      } catch (Exception e) {
        closeDueToException(info);
        throw new SQLException(e.getMessage());
      }
    }
    if (!(null == password ? null == info.getPassword() : password.equals(info.getPassword()))) {
      closeDueToException(info);
      throw new SQLException(
          "Given password did not match password used " + "to create the PooledConnection.");
    }
    PooledConnection pc = info.getPooledConnection();

    boolean defaultAutoCommit = isDefaultAutoCommit();
    if (username != null) {
      Boolean userMax = getPerUserDefaultAutoCommit(username);
      if (userMax != null) {
        defaultAutoCommit = userMax.booleanValue();
      }
    }

    boolean defaultReadOnly = isDefaultReadOnly();
    if (username != null) {
      Boolean userMax = getPerUserDefaultReadOnly(username);
      if (userMax != null) {
        defaultReadOnly = userMax.booleanValue();
      }
    }

    Connection con = pc.getConnection();
    con.setAutoCommit(defaultAutoCommit);
    con.setReadOnly(defaultReadOnly);
    return con;
  }
コード例 #8
0
  /**
   * Attempt to retrieve a database connection using {@link #getPooledConnectionAndInfo(String,
   * String)} with the provided username and password. The password on the {@link
   * PooledConnectionAndInfo} instance returned by <code>getPooledConnectionAndInfo</code> is
   * compared to the <code>password</code> parameter. If the comparison fails, a database connection
   * using the supplied username and password is attempted. If the connection attempt fails, an
   * SQLException is thrown, indicating that the given password did not match the password used to
   * create the pooled connection. If the connection attempt succeeds, this means that the database
   * password has been changed. In this case, the <code>PooledConnectionAndInfo</code> instance
   * retrieved with the old password is destroyed and the <code>getPooledConnectionAndInfo</code> is
   * repeatedly invoked until a <code>PooledConnectionAndInfo</code> instance with the new password
   * is returned.
   */
  @Override
  public Connection getConnection(String username, String password) throws SQLException {
    if (instanceKey == null) {
      throw new SQLException(
          "Must set the ConnectionPoolDataSource "
              + "through setDataSourceName or setConnectionPoolDataSource"
              + " before calling getConnection.");
    }
    getConnectionCalled = true;
    PooledConnectionAndInfo info = null;
    try {
      info = getPooledConnectionAndInfo(username, password);
    } catch (NoSuchElementException e) {
      closeDueToException(info);
      throw new SQLException("Cannot borrow connection from pool", e);
    } catch (RuntimeException e) {
      closeDueToException(info);
      throw e;
    } catch (SQLException e) {
      closeDueToException(info);
      throw e;
    } catch (Exception e) {
      closeDueToException(info);
      throw new SQLException("Cannot borrow connection from pool", e);
    }

    if (!(null == password
        ? null == info.getPassword()
        : password.equals(
            info.getPassword()))) { // Password on PooledConnectionAndInfo does not match
      try { // See if password has changed by attempting connection
        testCPDS(username, password);
      } catch (SQLException ex) {
        // Password has not changed, so refuse client, but return connection to the pool
        closeDueToException(info);
        throw new SQLException(
            "Given password did not match password used" + " to create the PooledConnection.", ex);
      } catch (javax.naming.NamingException ne) {
        throw new SQLException("NamingException encountered connecting to database", ne);
      }
      /*
       * Password must have changed -> destroy connection and keep retrying until we get a new, good one,
       * destroying any idle connections with the old passowrd as we pull them from the pool.
       */
      final UserPassKey upkey = info.getUserPassKey();
      final PooledConnectionManager manager = getConnectionManager(upkey);
      manager.invalidate(info.getPooledConnection()); // Destroy and remove from pool
      manager.setPassword(
          upkey.getPassword()); // Reset the password on the factory if using CPDSConnectionFactory
      info = null;
      for (int i = 0;
          i < 10;
          i++) { // Bound the number of retries - only needed if bad instances return
        try {
          info = getPooledConnectionAndInfo(username, password);
        } catch (NoSuchElementException e) {
          closeDueToException(info);
          throw new SQLException("Cannot borrow connection from pool", e);
        } catch (RuntimeException e) {
          closeDueToException(info);
          throw e;
        } catch (SQLException e) {
          closeDueToException(info);
          throw e;
        } catch (Exception e) {
          closeDueToException(info);
          throw new SQLException("Cannot borrow connection from pool", e);
        }
        if (info != null && password != null && password.equals(info.getPassword())) {
          break;
        }
        if (info != null) {
          manager.invalidate(info.getPooledConnection());
        }
        info = null;
      }
      if (info == null) {
        throw new SQLException("Cannot borrow connection from pool - password change failure.");
      }
    }

    Connection con = info.getPooledConnection().getConnection();
    try {
      setupDefaults(con, username);
      con.clearWarnings();
      return con;
    } catch (SQLException ex) {
      try {
        con.close();
      } catch (Exception exc) {
        getLogWriter().println("ignoring exception during close: " + exc);
      }
      throw ex;
    }
  }