Return-Path: X-Original-To: apmail-incubator-connectors-commits-archive@minotaur.apache.org Delivered-To: apmail-incubator-connectors-commits-archive@minotaur.apache.org Received: from mail.apache.org (hermes.apache.org [140.211.11.3]) by minotaur.apache.org (Postfix) with SMTP id 2D695C78C for ; Wed, 9 May 2012 06:20:54 +0000 (UTC) Received: (qmail 26066 invoked by uid 500); 9 May 2012 06:20:53 -0000 Delivered-To: apmail-incubator-connectors-commits-archive@incubator.apache.org Received: (qmail 26013 invoked by uid 500); 9 May 2012 06:20:52 -0000 Mailing-List: contact connectors-commits-help@incubator.apache.org; run by ezmlm Precedence: bulk List-Help: List-Unsubscribe: List-Post: List-Id: Reply-To: connectors-dev@incubator.apache.org Delivered-To: mailing list connectors-commits@incubator.apache.org Received: (qmail 25970 invoked by uid 99); 9 May 2012 06:20:50 -0000 Received: from athena.apache.org (HELO athena.apache.org) (140.211.11.136) by apache.org (qpsmtpd/0.29) with ESMTP; Wed, 09 May 2012 06:20:50 +0000 X-ASF-Spam-Status: No, hits=-1999.6 required=5.0 tests=ALL_TRUSTED,FILL_THIS_FORM_FRAUD_PHISH,T_FILL_THIS_FORM_SHORT X-Spam-Check-By: apache.org Received: from [140.211.11.4] (HELO eris.apache.org) (140.211.11.4) by apache.org (qpsmtpd/0.29) with ESMTP; Wed, 09 May 2012 06:20:44 +0000 Received: from eris.apache.org (localhost [127.0.0.1]) by eris.apache.org (Postfix) with ESMTP id B1F462388847; Wed, 9 May 2012 06:20:24 +0000 (UTC) Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit Subject: svn commit: r1335941 - in /incubator/lcf/branches/CONNECTORS-96: connectors/jdbc/connector/src/main/java/org/apache/manifoldcf/crawler/connectors/jdbc/ framework/core/src/main/java/org/apache/manifoldcf/core/jdbcpool/ Date: Wed, 09 May 2012 06:20:24 -0000 To: connectors-commits@incubator.apache.org From: kwright@apache.org X-Mailer: svnmailer-1.0.8-patched Message-Id: <20120509062024.B1F462388847@eris.apache.org> X-Virus-Checked: Checked by ClamAV on apache.org Author: kwright Date: Wed May 9 06:20:24 2012 New Revision: 1335941 URL: http://svn.apache.org/viewvc?rev=1335941&view=rev Log: Add connection expiration to pool. Modified: incubator/lcf/branches/CONNECTORS-96/connectors/jdbc/connector/src/main/java/org/apache/manifoldcf/crawler/connectors/jdbc/JDBCConnectionFactory.java incubator/lcf/branches/CONNECTORS-96/framework/core/src/main/java/org/apache/manifoldcf/core/jdbcpool/ConnectionPool.java incubator/lcf/branches/CONNECTORS-96/framework/core/src/main/java/org/apache/manifoldcf/core/jdbcpool/ConnectionPoolManager.java Modified: incubator/lcf/branches/CONNECTORS-96/connectors/jdbc/connector/src/main/java/org/apache/manifoldcf/crawler/connectors/jdbc/JDBCConnectionFactory.java URL: http://svn.apache.org/viewvc/incubator/lcf/branches/CONNECTORS-96/connectors/jdbc/connector/src/main/java/org/apache/manifoldcf/crawler/connectors/jdbc/JDBCConnectionFactory.java?rev=1335941&r1=1335940&r2=1335941&view=diff ============================================================================== --- incubator/lcf/branches/CONNECTORS-96/connectors/jdbc/connector/src/main/java/org/apache/manifoldcf/crawler/connectors/jdbc/JDBCConnectionFactory.java (original) +++ incubator/lcf/branches/CONNECTORS-96/connectors/jdbc/connector/src/main/java/org/apache/manifoldcf/crawler/connectors/jdbc/JDBCConnectionFactory.java Wed May 9 06:20:24 2012 @@ -122,7 +122,7 @@ public class JDBCConnectionFactory Class.forName(driverClassName); System.out.println("Class name '"+driverClassName+"'; URL = '"+dburl+"'"); cp =_pool.addAlias(poolKey, driverClassName, dburl, - userName, password, 30); + userName, password, 30, 300000L); } } return cp.getConnection(); Modified: incubator/lcf/branches/CONNECTORS-96/framework/core/src/main/java/org/apache/manifoldcf/core/jdbcpool/ConnectionPool.java URL: http://svn.apache.org/viewvc/incubator/lcf/branches/CONNECTORS-96/framework/core/src/main/java/org/apache/manifoldcf/core/jdbcpool/ConnectionPool.java?rev=1335941&r1=1335940&r2=1335941&view=diff ============================================================================== --- incubator/lcf/branches/CONNECTORS-96/framework/core/src/main/java/org/apache/manifoldcf/core/jdbcpool/ConnectionPool.java (original) +++ incubator/lcf/branches/CONNECTORS-96/framework/core/src/main/java/org/apache/manifoldcf/core/jdbcpool/ConnectionPool.java Wed May 9 06:20:24 2012 @@ -36,16 +36,20 @@ public class ConnectionPool protected volatile int freePointer; protected volatile int activeConnections; protected Connection[] freeConnections; + protected long[] connectionCleanupTimeouts; + protected long expiration; /** Constructor */ - public ConnectionPool(String dbURL, String userName, String password, int maxConnections) + public ConnectionPool(String dbURL, String userName, String password, int maxConnections, long expiration) { this.dbURL = dbURL; this.userName = userName; this.password = password; this.freeConnections = new Connection[maxConnections]; + this.connectionCleanupTimeouts = new long[maxConnections]; this.freePointer = 0; this.activeConnections = 0; + this.expiration = expiration; } /** Obtain a connection from the pool. @@ -113,9 +117,45 @@ public class ConnectionPool } } - protected synchronized void releaseConnection(Connection connection) + /** Clean up expired connections. + */ + public synchronized void cleanupExpiredConnections(long currentTime) + { + int i = 0; + while (i < freePointer) + { + if (connectionCleanupTimeouts[i] <= currentTime) + { + try + { + freeConnections[i].close(); + } + catch (SQLException e) + { + Logging.db.warn("Error closing pooled connection: "+e.getMessage(),e); + } + freePointer--; + if (freePointer == i) + { + freeConnections[i] = null; + } + else + { + freeConnections[i] = freeConnections[freePointer]; + connectionCleanupTimeouts[i] = connectionCleanupTimeouts[freePointer]; + freeConnections[freePointer] = null; + } + } + else + i++; + } + } + + public synchronized void releaseConnection(Connection connection) { - freeConnections[freePointer++] = connection; + freeConnections[freePointer] = connection; + connectionCleanupTimeouts[freePointer] = System.currentTimeMillis() + expiration; + freePointer++; notifyAll(); } Modified: incubator/lcf/branches/CONNECTORS-96/framework/core/src/main/java/org/apache/manifoldcf/core/jdbcpool/ConnectionPoolManager.java URL: http://svn.apache.org/viewvc/incubator/lcf/branches/CONNECTORS-96/framework/core/src/main/java/org/apache/manifoldcf/core/jdbcpool/ConnectionPoolManager.java?rev=1335941&r1=1335940&r2=1335941&view=diff ============================================================================== --- incubator/lcf/branches/CONNECTORS-96/framework/core/src/main/java/org/apache/manifoldcf/core/jdbcpool/ConnectionPoolManager.java (original) +++ incubator/lcf/branches/CONNECTORS-96/framework/core/src/main/java/org/apache/manifoldcf/core/jdbcpool/ConnectionPoolManager.java Wed May 9 06:20:24 2012 @@ -21,7 +21,7 @@ package org.apache.manifoldcf.core.jdbcp import javax.naming.*; import javax.sql.*; import java.util.*; - +import java.util.concurrent.atomic.AtomicBoolean; /** An instance of this class manages a number of (independent) connection pools. */ @@ -30,10 +30,14 @@ public class ConnectionPoolManager public static final String _rcsid = "@(#)$Id$"; protected Map poolMap; + protected ConnectionCloserThread connectionCloserThread; + protected AtomicBoolean shuttingDown = new AtomicBoolean(false); public ConnectionPoolManager(int count) { poolMap = new HashMap(count); + connectionCloserThread = new ConnectionCloserThread(); + connectionCloserThread.start(); } /** Look for a pool with a given key. @@ -46,15 +50,82 @@ public class ConnectionPoolManager /** Set up a pool with a given key. */ public synchronized ConnectionPool addAlias(String poolKey, String driverClassName, String dbURL, - String userName, String password, int maxSize) + String userName, String password, int maxSize, long expiration) throws ClassNotFoundException, InstantiationException, IllegalAccessException { Class.forName(driverClassName); - ConnectionPool cp = new ConnectionPool(driverClassName,userName,password,maxSize); + ConnectionPool cp = new ConnectionPool(driverClassName,userName,password,maxSize,expiration); poolMap.put(poolKey,cp); return cp; } + public synchronized void shutdown() + { + shuttingDown.set(true); + while (connectionCloserThread.isAlive()) + { + try + { + Thread.sleep(1000L); + } + catch (InterruptedException e) + { + // Ignore this until the thread is down + connectionCloserThread.interrupt(); + } + } + Iterator iter = poolMap.keySet().iterator(); + while (iter.hasNext()) + { + String poolKey = iter.next(); + ConnectionPool cp = poolMap.get(poolKey); + cp.closePool(); + } + } + + protected synchronized void cleanupExpiredConnections(long cleanupTime) + { + Iterator iter = poolMap.keySet().iterator(); + while (iter.hasNext()) + { + String poolKey = iter.next(); + ConnectionPool cp = poolMap.get(poolKey); + cp.cleanupExpiredConnections(cleanupTime); + } + } + + protected class ConnectionCloserThread extends Thread + { + + public ConnectionCloserThread() + { + super(); + setName("Connection pool reaper"); + setDaemon(true); + } + + public void run() + { + while (true) + { + cleanupExpiredConnections(System.currentTimeMillis()); + if (shuttingDown.get()) + break; + try + { + Thread.sleep(60000L); + } + catch (InterruptedException e) + { + break; + } + } + + } + + } + + }