Source Code Cross Referenced for GenericKeyedObjectPool.java in  » Database-JDBC-Connection-Pool » Apache-commons-pool-1.3 » org » apache » commons » pool » impl » Java Source Code / Java DocumentationJava Source Code and Java Documentation

Java Source Code / Java Documentation
1. 6.0 JDK Core
2. 6.0 JDK Modules
3. 6.0 JDK Modules com.sun
4. 6.0 JDK Modules com.sun.java
5. 6.0 JDK Modules sun
6. 6.0 JDK Platform
7. Ajax
8. Apache Harmony Java SE
9. Aspect oriented
10. Authentication Authorization
11. Blogger System
12. Build
13. Byte Code
14. Cache
15. Chart
16. Chat
17. Code Analyzer
18. Collaboration
19. Content Management System
20. Database Client
21. Database DBMS
22. Database JDBC Connection Pool
23. Database ORM
24. Development
25. EJB Server geronimo
26. EJB Server GlassFish
27. EJB Server JBoss 4.2.1
28. EJB Server resin 3.1.5
29. ERP CRM Financial
30. ESB
31. Forum
32. GIS
33. Graphic Library
34. Groupware
35. HTML Parser
36. IDE
37. IDE Eclipse
38. IDE Netbeans
39. Installer
40. Internationalization Localization
41. Inversion of Control
42. Issue Tracking
43. J2EE
44. JBoss
45. JMS
46. JMX
47. Library
48. Mail Clients
49. Net
50. Parser
51. PDF
52. Portal
53. Profiler
54. Project Management
55. Report
56. RSS RDF
57. Rule Engine
58. Science
59. Scripting
60. Search Engine
61. Security
62. Sevlet Container
63. Source Control
64. Swing Library
65. Template Engine
66. Test Coverage
67. Testing
68. UML
69. Web Crawler
70. Web Framework
71. Web Mail
72. Web Server
73. Web Services
74. Web Services apache cxf 2.0.1
75. Web Services AXIS2
76. Wiki Engine
77. Workflow Engines
78. XML
79. XML UI
Java
Java Tutorial
Java Open Source
Jar File Download
Java Articles
Java Products
Java by API
Photoshop Tutorials
Maya Tutorials
Flash Tutorials
3ds-Max Tutorials
Illustrator Tutorials
GIMP Tutorials
C# / C Sharp
C# / CSharp Tutorial
C# / CSharp Open Source
ASP.Net
ASP.NET Tutorial
JavaScript DHTML
JavaScript Tutorial
JavaScript Reference
HTML / CSS
HTML CSS Reference
C / ANSI-C
C Tutorial
C++
C++ Tutorial
Ruby
PHP
Python
Python Tutorial
Python Open Source
SQL Server / T-SQL
SQL Server / T-SQL Tutorial
Oracle PL / SQL
Oracle PL/SQL Tutorial
PostgreSQL
SQL / MySQL
MySQL Tutorial
VB.Net
VB.Net Tutorial
Flash / Flex / ActionScript
VBA / Excel / Access / Word
XML
XML Tutorial
Microsoft Office PowerPoint 2007 Tutorial
Microsoft Office Excel 2007 Tutorial
Microsoft Office Word 2007 Tutorial
Java Source Code / Java Documentation » Database JDBC Connection Pool » Apache commons pool 1.3 » org.apache.commons.pool.impl 
Source Cross Referenced  Class Diagram Java Document (Java Doc) 


0001:        /*
0002:         * Copyright 1999-2004,2006 The Apache Software Foundation.
0003:         * 
0004:         * Licensed under the Apache License, Version 2.0 (the "License");
0005:         * you may not use this file except in compliance with the License.
0006:         * You may obtain a copy of the License at
0007:         * 
0008:         *      http://www.apache.org/licenses/LICENSE-2.0
0009:         * 
0010:         * Unless required by applicable law or agreed to in writing, software
0011:         * distributed under the License is distributed on an "AS IS" BASIS,
0012:         * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
0013:         * See the License for the specific language governing permissions and
0014:         * limitations under the License.
0015:         */
0016:
0017:        package org.apache.commons.pool.impl;
0018:
0019:        import java.util.HashMap;
0020:        import java.util.Iterator;
0021:        import java.util.ListIterator;
0022:        import java.util.Map;
0023:        import java.util.NoSuchElementException;
0024:        import java.util.Set;
0025:        import java.util.TreeMap;
0026:        import java.util.LinkedList;
0027:        import java.util.HashSet;
0028:        import java.util.TimerTask;
0029:
0030:        import org.apache.commons.pool.BaseKeyedObjectPool;
0031:        import org.apache.commons.pool.KeyedObjectPool;
0032:        import org.apache.commons.pool.KeyedPoolableObjectFactory;
0033:
0034:        /**
0035:         * A configurable {@link KeyedObjectPool} implementation.
0036:         * <p>
0037:         * When coupled with the appropriate {@link KeyedPoolableObjectFactory},
0038:         * <tt>GenericKeyedObjectPool</tt> provides robust pooling functionality for
0039:         * arbitrary objects.
0040:         * <p>
0041:         * A <tt>GenericKeyedObjectPool</tt> provides a number of configurable parameters:
0042:         * <ul>
0043:         *  <li>
0044:         *    {@link #setMaxActive <i>maxActive</i>} controls the maximum number of objects (per key)
0045:         *    that can be borrowed from the pool at one time.  When non-positive, there
0046:         *    is no limit to the number of objects that may be active at one time.
0047:         *    When {@link #setMaxActive <i>maxActive</i>} is exceeded, the pool is said to be exhausted.
0048:         *  </li>
0049:         *  <li>
0050:         *    {@link #setMaxIdle <i>maxIdle</i>} controls the maximum number of objects that can
0051:         *    sit idle in the pool (per key) at any time.  When negative, there
0052:         *    is no limit to the number of objects that may be idle at one time.
0053:         *  </li>
0054:         *  <li>
0055:         *    {@link #setWhenExhaustedAction <i>whenExhaustedAction</i>} specifies the
0056:         *    behaviour of the {@link #borrowObject} method when the pool is exhausted:
0057:         *    <ul>
0058:         *    <li>
0059:         *      When {@link #setWhenExhaustedAction <i>whenExhaustedAction</i>} is
0060:         *      {@link #WHEN_EXHAUSTED_FAIL}, {@link #borrowObject} will throw
0061:         *      a {@link NoSuchElementException}
0062:         *    </li>
0063:         *    <li>
0064:         *      When {@link #setWhenExhaustedAction <i>whenExhaustedAction</i>} is
0065:         *      {@link #WHEN_EXHAUSTED_GROW}, {@link #borrowObject} will create a new
0066:         *      object and return it(essentially making {@link #setMaxActive <i>maxActive</i>}
0067:         *      meaningless.)
0068:         *    </li>
0069:         *    <li>
0070:         *      When {@link #setWhenExhaustedAction <i>whenExhaustedAction</i>}
0071:         *      is {@link #WHEN_EXHAUSTED_BLOCK}, {@link #borrowObject} will block
0072:         *      (invoke {@link Object#wait} until a new or idle object is available.
0073:         *      If a positive {@link #setMaxWait <i>maxWait</i>}
0074:         *      value is supplied, the {@link #borrowObject} will block for at
0075:         *      most that many milliseconds, after which a {@link NoSuchElementException}
0076:         *      will be thrown.  If {@link #setMaxWait <i>maxWait</i>} is non-positive,
0077:         *      the {@link #borrowObject} method will block indefinitely.
0078:         *    </li>
0079:         *    </ul>
0080:         *  </li>
0081:         *  <li>
0082:         *    When {@link #setTestOnBorrow <i>testOnBorrow</i>} is set, the pool will
0083:         *    attempt to validate each object before it is returned from the
0084:         *    {@link #borrowObject} method. (Using the provided factory's
0085:         *    {@link KeyedPoolableObjectFactory#validateObject} method.)  Objects that fail
0086:         *    to validate will be dropped from the pool, and a different object will
0087:         *    be borrowed.
0088:         *  </li>
0089:         *  <li>
0090:         *    When {@link #setTestOnReturn <i>testOnReturn</i>} is set, the pool will
0091:         *    attempt to validate each object before it is returned to the pool in the
0092:         *    {@link #returnObject} method. (Using the provided factory's
0093:         *    {@link KeyedPoolableObjectFactory#validateObject}
0094:         *    method.)  Objects that fail to validate will be dropped from the pool.
0095:         *  </li>
0096:         * </ul>
0097:         * <p>
0098:         * Optionally, one may configure the pool to examine and possibly evict objects as they
0099:         * sit idle in the pool.  This is performed by an "idle object eviction" thread, which
0100:         * runs asychronously.  The idle object eviction thread may be configured using the
0101:         * following attributes:
0102:         * <ul>
0103:         *  <li>
0104:         *   {@link #setTimeBetweenEvictionRunsMillis <i>timeBetweenEvictionRunsMillis</i>}
0105:         *   indicates how long the eviction thread should sleep before "runs" of examining
0106:         *   idle objects.  When non-positive, no eviction thread will be launched.
0107:         *  </li>
0108:         *  <li>
0109:         *   {@link #setMinEvictableIdleTimeMillis <i>minEvictableIdleTimeMillis</i>}
0110:         *   specifies the minimum amount of time that an object may sit idle in the pool
0111:         *   before it is eligable for eviction due to idle time.  When non-positive, no object
0112:         *   will be dropped from the pool due to idle time alone.
0113:         *  </li>
0114:         *  <li>
0115:         *   {@link #setTestWhileIdle <i>testWhileIdle</i>} indicates whether or not idle
0116:         *   objects should be validated using the factory's
0117:         *   {@link KeyedPoolableObjectFactory#validateObject} method.  Objects
0118:         *   that fail to validate will be dropped from the pool.
0119:         *  </li>
0120:         * </ul>
0121:         * <p>
0122:         * GenericKeyedObjectPool is not usable without a {@link KeyedPoolableObjectFactory}.  A
0123:         * non-<code>null</code> factory must be provided either as a constructor argument
0124:         * or via a call to {@link #setFactory} before the pool is used.
0125:         * </p>
0126:         * @see GenericObjectPool
0127:         * @author Rodney Waldhoff
0128:         * @author Dirk Verbeeck
0129:         * @version $Revision: 386116 $ $Date: 2006-03-15 12:15:58 -0500 (Wed, 15 Mar 2006) $
0130:         */
0131:        public class GenericKeyedObjectPool extends BaseKeyedObjectPool
0132:                implements  KeyedObjectPool {
0133:
0134:            //--- public constants -------------------------------------------
0135:
0136:            /**
0137:             * A "when exhausted action" type indicating that when the pool is
0138:             * exhausted (i.e., the maximum number of active objects has
0139:             * been reached), the {@link #borrowObject}
0140:             * method should fail, throwing a {@link NoSuchElementException}.
0141:             * @see #WHEN_EXHAUSTED_BLOCK
0142:             * @see #WHEN_EXHAUSTED_GROW
0143:             * @see #setWhenExhaustedAction
0144:             */
0145:            public static final byte WHEN_EXHAUSTED_FAIL = 0;
0146:
0147:            /**
0148:             * A "when exhausted action" type indicating that when the pool
0149:             * is exhausted (i.e., the maximum number
0150:             * of active objects has been reached), the {@link #borrowObject}
0151:             * method should block until a new object is available, or the
0152:             * {@link #getMaxWait maximum wait time} has been reached.
0153:             * @see #WHEN_EXHAUSTED_FAIL
0154:             * @see #WHEN_EXHAUSTED_GROW
0155:             * @see #setMaxWait
0156:             * @see #getMaxWait
0157:             * @see #setWhenExhaustedAction
0158:             */
0159:            public static final byte WHEN_EXHAUSTED_BLOCK = 1;
0160:
0161:            /**
0162:             * A "when exhausted action" type indicating that when the pool is
0163:             * exhausted (i.e., the maximum number
0164:             * of active objects has been reached), the {@link #borrowObject}
0165:             * method should simply create a new object anyway.
0166:             * @see #WHEN_EXHAUSTED_FAIL
0167:             * @see #WHEN_EXHAUSTED_GROW
0168:             * @see #setWhenExhaustedAction
0169:             */
0170:            public static final byte WHEN_EXHAUSTED_GROW = 2;
0171:
0172:            /**
0173:             * The default cap on the number of idle instances in the pool
0174:             * (per key).
0175:             * @see #getMaxIdle
0176:             * @see #setMaxIdle
0177:             */
0178:            public static final int DEFAULT_MAX_IDLE = 8;
0179:
0180:            /**
0181:             * The default cap on the total number of active instances from the pool
0182:             * (per key).
0183:             * @see #getMaxActive
0184:             * @see #setMaxActive
0185:             */
0186:            public static final int DEFAULT_MAX_ACTIVE = 8;
0187:
0188:            /**
0189:             * The default cap on the the maximum number of objects that can exists at one time.
0190:             * @see #getMaxTotal
0191:             * @see #setMaxTotal
0192:             */
0193:            public static final int DEFAULT_MAX_TOTAL = -1;
0194:
0195:            /**
0196:             * The default "when exhausted action" for the pool.
0197:             * @see #WHEN_EXHAUSTED_BLOCK
0198:             * @see #WHEN_EXHAUSTED_FAIL
0199:             * @see #WHEN_EXHAUSTED_GROW
0200:             * @see #setWhenExhaustedAction
0201:             */
0202:            public static final byte DEFAULT_WHEN_EXHAUSTED_ACTION = WHEN_EXHAUSTED_BLOCK;
0203:
0204:            /**
0205:             * The default maximum amount of time (in millis) the
0206:             * {@link #borrowObject} method should block before throwing
0207:             * an exception when the pool is exhausted and the
0208:             * {@link #getWhenExhaustedAction "when exhausted" action} is
0209:             * {@link #WHEN_EXHAUSTED_BLOCK}.
0210:             * @see #getMaxWait
0211:             * @see #setMaxWait
0212:             */
0213:            public static final long DEFAULT_MAX_WAIT = -1L;
0214:
0215:            /**
0216:             * The default "test on borrow" value.
0217:             * @see #getTestOnBorrow
0218:             * @see #setTestOnBorrow
0219:             */
0220:            public static final boolean DEFAULT_TEST_ON_BORROW = false;
0221:
0222:            /**
0223:             * The default "test on return" value.
0224:             * @see #getTestOnReturn
0225:             * @see #setTestOnReturn
0226:             */
0227:            public static final boolean DEFAULT_TEST_ON_RETURN = false;
0228:
0229:            /**
0230:             * The default "test while idle" value.
0231:             * @see #getTestWhileIdle
0232:             * @see #setTestWhileIdle
0233:             * @see #getTimeBetweenEvictionRunsMillis
0234:             * @see #setTimeBetweenEvictionRunsMillis
0235:             */
0236:            public static final boolean DEFAULT_TEST_WHILE_IDLE = false;
0237:
0238:            /**
0239:             * The default "time between eviction runs" value.
0240:             * @see #getTimeBetweenEvictionRunsMillis
0241:             * @see #setTimeBetweenEvictionRunsMillis
0242:             */
0243:            public static final long DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS = -1L;
0244:
0245:            /**
0246:             * The default number of objects to examine per run in the
0247:             * idle object evictor.
0248:             * @see #getNumTestsPerEvictionRun
0249:             * @see #setNumTestsPerEvictionRun
0250:             * @see #getTimeBetweenEvictionRunsMillis
0251:             * @see #setTimeBetweenEvictionRunsMillis
0252:             */
0253:            public static final int DEFAULT_NUM_TESTS_PER_EVICTION_RUN = 3;
0254:
0255:            /**
0256:             * The default value for {@link #getMinEvictableIdleTimeMillis}.
0257:             * @see #getMinEvictableIdleTimeMillis
0258:             * @see #setMinEvictableIdleTimeMillis
0259:             */
0260:            public static final long DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS = 1000L * 60L * 30L;
0261:
0262:            /**
0263:             * The default minimum level of idle objects in the pool.
0264:             * @see #setMinIdle
0265:             * @see #getMinIdle
0266:             */
0267:            public static final int DEFAULT_MIN_IDLE = 0;
0268:
0269:            //--- constructors -----------------------------------------------
0270:
0271:            /**
0272:             * Create a new <tt>GenericKeyedObjectPool</tt>..
0273:             */
0274:            public GenericKeyedObjectPool() {
0275:                this (null, DEFAULT_MAX_ACTIVE, DEFAULT_WHEN_EXHAUSTED_ACTION,
0276:                        DEFAULT_MAX_WAIT, DEFAULT_MAX_IDLE,
0277:                        DEFAULT_TEST_ON_BORROW, DEFAULT_TEST_ON_RETURN,
0278:                        DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS,
0279:                        DEFAULT_NUM_TESTS_PER_EVICTION_RUN,
0280:                        DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS,
0281:                        DEFAULT_TEST_WHILE_IDLE);
0282:            }
0283:
0284:            /**
0285:             * Create a new <tt>GenericKeyedObjectPool</tt> using the specified values.
0286:             * @param factory the (possibly <tt>null</tt>)KeyedPoolableObjectFactory to use to create, validate and destroy objects
0287:             */
0288:            public GenericKeyedObjectPool(KeyedPoolableObjectFactory factory) {
0289:                this (factory, DEFAULT_MAX_ACTIVE,
0290:                        DEFAULT_WHEN_EXHAUSTED_ACTION, DEFAULT_MAX_WAIT,
0291:                        DEFAULT_MAX_IDLE, DEFAULT_TEST_ON_BORROW,
0292:                        DEFAULT_TEST_ON_RETURN,
0293:                        DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS,
0294:                        DEFAULT_NUM_TESTS_PER_EVICTION_RUN,
0295:                        DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS,
0296:                        DEFAULT_TEST_WHILE_IDLE);
0297:            }
0298:
0299:            /**
0300:             * Create a new <tt>GenericKeyedObjectPool</tt> using the specified values.
0301:             * @param factory the (possibly <tt>null</tt>)KeyedPoolableObjectFactory to use to create, validate and destroy objects
0302:             * @param config a non-<tt>null</tt> {@link GenericKeyedObjectPool.Config} describing my configuration
0303:             */
0304:            public GenericKeyedObjectPool(KeyedPoolableObjectFactory factory,
0305:                    GenericKeyedObjectPool.Config config) {
0306:                this (factory, config.maxActive, config.whenExhaustedAction,
0307:                        config.maxWait, config.maxIdle, config.maxTotal,
0308:                        config.testOnBorrow, config.testOnReturn,
0309:                        config.timeBetweenEvictionRunsMillis,
0310:                        config.numTestsPerEvictionRun,
0311:                        config.minEvictableIdleTimeMillis, config.testWhileIdle);
0312:            }
0313:
0314:            /**
0315:             * Create a new <tt>GenericKeyedObjectPool</tt> using the specified values.
0316:             * @param factory the (possibly <tt>null</tt>)KeyedPoolableObjectFactory to use to create, validate and destroy objects
0317:             * @param maxActive the maximum number of objects that can be borrowed from me at one time (per key) (see {@link #setMaxActive})
0318:             */
0319:            public GenericKeyedObjectPool(KeyedPoolableObjectFactory factory,
0320:                    int maxActive) {
0321:                this (factory, maxActive, DEFAULT_WHEN_EXHAUSTED_ACTION,
0322:                        DEFAULT_MAX_WAIT, DEFAULT_MAX_IDLE,
0323:                        DEFAULT_TEST_ON_BORROW, DEFAULT_TEST_ON_RETURN,
0324:                        DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS,
0325:                        DEFAULT_NUM_TESTS_PER_EVICTION_RUN,
0326:                        DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS,
0327:                        DEFAULT_TEST_WHILE_IDLE);
0328:            }
0329:
0330:            /**
0331:             * Create a new <tt>GenericKeyedObjectPool</tt> using the specified values.
0332:             * @param factory the (possibly <tt>null</tt>)KeyedPoolableObjectFactory to use to create, validate and destroy objects
0333:             * @param maxActive the maximum number of objects that can be borrowed from me at one time (per key) (see {@link #setMaxActive})
0334:             * @param whenExhaustedAction the action to take when the pool is exhausted (see {@link #setWhenExhaustedAction})
0335:             * @param maxWait the maximum amount of time to wait for an idle object when the pool is exhausted an and <i>whenExhaustedAction</i> is {@link #WHEN_EXHAUSTED_BLOCK} (otherwise ignored) (see {@link #setMaxWait})
0336:             */
0337:            public GenericKeyedObjectPool(KeyedPoolableObjectFactory factory,
0338:                    int maxActive, byte whenExhaustedAction, long maxWait) {
0339:                this (factory, maxActive, whenExhaustedAction, maxWait,
0340:                        DEFAULT_MAX_IDLE, DEFAULT_TEST_ON_BORROW,
0341:                        DEFAULT_TEST_ON_RETURN,
0342:                        DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS,
0343:                        DEFAULT_NUM_TESTS_PER_EVICTION_RUN,
0344:                        DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS,
0345:                        DEFAULT_TEST_WHILE_IDLE);
0346:            }
0347:
0348:            /**
0349:             * Create a new <tt>GenericKeyedObjectPool</tt> using the specified values.
0350:             * @param factory the (possibly <tt>null</tt>)KeyedPoolableObjectFactory to use to create, validate and destroy objects
0351:             * @param maxActive the maximum number of objects that can be borrowed from me at one time (per key) (see {@link #setMaxActive})
0352:             * @param maxWait the maximum amount of time to wait for an idle object when the pool is exhausted an and <i>whenExhaustedAction</i> is {@link #WHEN_EXHAUSTED_BLOCK} (otherwise ignored) (see {@link #setMaxWait})
0353:             * @param whenExhaustedAction the action to take when the pool is exhausted (see {@link #setWhenExhaustedAction})
0354:             * @param testOnBorrow whether or not to validate objects before they are returned by the {@link #borrowObject} method (see {@link #setTestOnBorrow})
0355:             * @param testOnReturn whether or not to validate objects after they are returned to the {@link #returnObject} method (see {@link #setTestOnReturn})
0356:             */
0357:            public GenericKeyedObjectPool(KeyedPoolableObjectFactory factory,
0358:                    int maxActive, byte whenExhaustedAction, long maxWait,
0359:                    boolean testOnBorrow, boolean testOnReturn) {
0360:                this (factory, maxActive, whenExhaustedAction, maxWait,
0361:                        DEFAULT_MAX_IDLE, testOnBorrow, testOnReturn,
0362:                        DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS,
0363:                        DEFAULT_NUM_TESTS_PER_EVICTION_RUN,
0364:                        DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS,
0365:                        DEFAULT_TEST_WHILE_IDLE);
0366:            }
0367:
0368:            /**
0369:             * Create a new <tt>GenericKeyedObjectPool</tt> using the specified values.
0370:             * @param factory the (possibly <tt>null</tt>)KeyedPoolableObjectFactory to use to create, validate and destroy objects
0371:             * @param maxActive the maximum number of objects that can be borrowed from me at one time (per key) (see {@link #setMaxActive})
0372:             * @param whenExhaustedAction the action to take when the pool is exhausted (see {@link #setWhenExhaustedAction})
0373:             * @param maxWait the maximum amount of time to wait for an idle object when the pool is exhausted an and <i>whenExhaustedAction</i> is {@link #WHEN_EXHAUSTED_BLOCK} (otherwise ignored) (see {@link #setMaxWait})
0374:             * @param maxIdle the maximum number of idle objects in my pool (per key) (see {@link #setMaxIdle})
0375:             */
0376:            public GenericKeyedObjectPool(KeyedPoolableObjectFactory factory,
0377:                    int maxActive, byte whenExhaustedAction, long maxWait,
0378:                    int maxIdle) {
0379:                this (factory, maxActive, whenExhaustedAction, maxWait, maxIdle,
0380:                        DEFAULT_TEST_ON_BORROW, DEFAULT_TEST_ON_RETURN,
0381:                        DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS,
0382:                        DEFAULT_NUM_TESTS_PER_EVICTION_RUN,
0383:                        DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS,
0384:                        DEFAULT_TEST_WHILE_IDLE);
0385:            }
0386:
0387:            /**
0388:             * Create a new <tt>GenericKeyedObjectPool</tt> using the specified values.
0389:             * @param factory the (possibly <tt>null</tt>)KeyedPoolableObjectFactory to use to create, validate and destroy objects
0390:             * @param maxActive the maximum number of objects that can be borrowed from me at one time (per key) (see {@link #setMaxActive})
0391:             * @param whenExhaustedAction the action to take when the pool is exhausted (see {@link #setWhenExhaustedAction})
0392:             * @param maxWait the maximum amount of time to wait for an idle object when the pool is exhausted an and <i>whenExhaustedAction</i> is {@link #WHEN_EXHAUSTED_BLOCK} (otherwise ignored) (see {@link #getMaxWait})
0393:             * @param maxIdle the maximum number of idle objects in my pool (see {@link #setMaxIdle})
0394:             * @param testOnBorrow whether or not to validate objects before they are returned by the {@link #borrowObject} method (see {@link #setTestOnBorrow})
0395:             * @param testOnReturn whether or not to validate objects after they are returned to the {@link #returnObject} method (see {@link #setTestOnReturn})
0396:             */
0397:            public GenericKeyedObjectPool(KeyedPoolableObjectFactory factory,
0398:                    int maxActive, byte whenExhaustedAction, long maxWait,
0399:                    int maxIdle, boolean testOnBorrow, boolean testOnReturn) {
0400:                this (factory, maxActive, whenExhaustedAction, maxWait, maxIdle,
0401:                        testOnBorrow, testOnReturn,
0402:                        DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS,
0403:                        DEFAULT_NUM_TESTS_PER_EVICTION_RUN,
0404:                        DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS,
0405:                        DEFAULT_TEST_WHILE_IDLE);
0406:            }
0407:
0408:            /**
0409:             * Create a new <tt>GenericKeyedObjectPool</tt> using the specified values.
0410:             * @param factory the (possibly <tt>null</tt>)PoolableObjectFactory to use to create, validate and destroy objects
0411:             * @param maxActive the maximum number of objects that can be borrowed from me at one time (per key) (see {@link #setMaxActive})
0412:             * @param whenExhaustedAction the action to take when the pool is exhausted (see {@link #setWhenExhaustedAction})
0413:             * @param maxWait the maximum amount of time to wait for an idle object when the pool is exhausted an and <i>whenExhaustedAction</i> is {@link #WHEN_EXHAUSTED_BLOCK} (otherwise ignored) (see {@link #setMaxWait})
0414:             * @param maxIdle the maximum number of idle objects in my pool (see {@link #setMaxIdle})
0415:             * @param testOnBorrow whether or not to validate objects before they are returned by the {@link #borrowObject} method (see {@link #setTestOnBorrow})
0416:             * @param testOnReturn whether or not to validate objects after they are returned to the {@link #returnObject} method (see {@link #setTestOnReturn})
0417:             * @param timeBetweenEvictionRunsMillis the amount of time (in milliseconds) to sleep between examining idle objects for eviction (see {@link #setTimeBetweenEvictionRunsMillis})
0418:             * @param numTestsPerEvictionRun the number of idle objects to examine per run within the idle object eviction thread (if any) (see {@link #setNumTestsPerEvictionRun})
0419:             * @param minEvictableIdleTimeMillis the minimum number of milliseconds an object can sit idle in the pool before it is eligable for evcition (see {@link #setMinEvictableIdleTimeMillis})
0420:             * @param testWhileIdle whether or not to validate objects in the idle object eviction thread, if any (see {@link #setTestWhileIdle})
0421:             */
0422:            public GenericKeyedObjectPool(KeyedPoolableObjectFactory factory,
0423:                    int maxActive, byte whenExhaustedAction, long maxWait,
0424:                    int maxIdle, boolean testOnBorrow, boolean testOnReturn,
0425:                    long timeBetweenEvictionRunsMillis,
0426:                    int numTestsPerEvictionRun,
0427:                    long minEvictableIdleTimeMillis, boolean testWhileIdle) {
0428:                this (factory, maxActive, whenExhaustedAction, maxWait, maxIdle,
0429:                        GenericKeyedObjectPool.DEFAULT_MAX_TOTAL, testOnBorrow,
0430:                        testOnReturn, timeBetweenEvictionRunsMillis,
0431:                        numTestsPerEvictionRun, minEvictableIdleTimeMillis,
0432:                        testWhileIdle);
0433:            }
0434:
0435:            /**
0436:             * Create a new <tt>GenericKeyedObjectPool</tt> using the specified values.
0437:             * @param factory the (possibly <tt>null</tt>)PoolableObjectFactory to use to create, validate and destroy objects
0438:             * @param maxActive the maximum number of objects that can be borrowed from me at one time (per key) (see {@link #setMaxActive})
0439:             * @param whenExhaustedAction the action to take when the pool is exhausted (see {@link #setWhenExhaustedAction})
0440:             * @param maxWait the maximum amount of time to wait for an idle object when the pool is exhausted an and <i>whenExhaustedAction</i> is {@link #WHEN_EXHAUSTED_BLOCK} (otherwise ignored) (see {@link #setMaxWait})
0441:             * @param maxIdle the maximum number of idle objects in my pool (see {@link #setMaxIdle})
0442:             * @param maxTotal the maximum number of objects that can exists at one time (see {@link #setMaxTotal})
0443:             * @param testOnBorrow whether or not to validate objects before they are returned by the {@link #borrowObject} method (see {@link #setTestOnBorrow})
0444:             * @param testOnReturn whether or not to validate objects after they are returned to the {@link #returnObject} method (see {@link #setTestOnReturn})
0445:             * @param timeBetweenEvictionRunsMillis the amount of time (in milliseconds) to sleep between examining idle objects for eviction (see {@link #setTimeBetweenEvictionRunsMillis})
0446:             * @param numTestsPerEvictionRun the number of idle objects to examine per run within the idle object eviction thread (if any) (see {@link #setNumTestsPerEvictionRun})
0447:             * @param minEvictableIdleTimeMillis the minimum number of milliseconds an object can sit idle in the pool before it is eligable for evcition (see {@link #setMinEvictableIdleTimeMillis})
0448:             * @param testWhileIdle whether or not to validate objects in the idle object eviction thread, if any (see {@link #setTestWhileIdle})
0449:             */
0450:            public GenericKeyedObjectPool(KeyedPoolableObjectFactory factory,
0451:                    int maxActive, byte whenExhaustedAction, long maxWait,
0452:                    int maxIdle, int maxTotal, boolean testOnBorrow,
0453:                    boolean testOnReturn, long timeBetweenEvictionRunsMillis,
0454:                    int numTestsPerEvictionRun,
0455:                    long minEvictableIdleTimeMillis, boolean testWhileIdle) {
0456:                this (factory, maxActive, whenExhaustedAction, maxWait, maxIdle,
0457:                        maxTotal, GenericKeyedObjectPool.DEFAULT_MIN_IDLE,
0458:                        testOnBorrow, testOnReturn,
0459:                        timeBetweenEvictionRunsMillis, numTestsPerEvictionRun,
0460:                        minEvictableIdleTimeMillis, testWhileIdle);
0461:            }
0462:
0463:            /**
0464:             * Create a new <tt>GenericKeyedObjectPool</tt> using the specified values.
0465:             * @param factory the (possibly <tt>null</tt>)PoolableObjectFactory to use to create, validate and destroy objects
0466:             * @param maxActive the maximum number of objects that can be borrowed from me at one time (per key) (see {@link #setMaxActive})
0467:             * @param whenExhaustedAction the action to take when the pool is exhausted (see {@link #setWhenExhaustedAction})
0468:             * @param maxWait the maximum amount of time to wait for an idle object when the pool is exhausted an and <i>whenExhaustedAction</i> is {@link #WHEN_EXHAUSTED_BLOCK} (otherwise ignored) (see {@link #setMaxWait})
0469:             * @param maxIdle the maximum number of idle objects in my pool (see {@link #setMaxIdle})
0470:             * @param maxTotal the maximum number of objects that can exists at one time (see {@link #setMaxTotal})
0471:             * @param minIdle the minimum number of idle objects to have in the pool at any one time (see {@link #setMinIdle})
0472:             * @param testOnBorrow whether or not to validate objects before they are returned by the {@link #borrowObject} method (see {@link #setTestOnBorrow})
0473:             * @param testOnReturn whether or not to validate objects after they are returned to the {@link #returnObject} method (see {@link #setTestOnReturn})
0474:             * @param timeBetweenEvictionRunsMillis the amount of time (in milliseconds) to sleep between examining idle objects for eviction (see {@link #setTimeBetweenEvictionRunsMillis})
0475:             * @param numTestsPerEvictionRun the number of idle objects to examine per run within the idle object eviction thread (if any) (see {@link #setNumTestsPerEvictionRun})
0476:             * @param minEvictableIdleTimeMillis the minimum number of milliseconds an object can sit idle in the pool before it is eligable for evcition (see {@link #setMinEvictableIdleTimeMillis})
0477:             * @param testWhileIdle whether or not to validate objects in the idle object eviction thread, if any (see {@link #setTestWhileIdle})
0478:             */
0479:            public GenericKeyedObjectPool(KeyedPoolableObjectFactory factory,
0480:                    int maxActive, byte whenExhaustedAction, long maxWait,
0481:                    int maxIdle, int maxTotal, int minIdle,
0482:                    boolean testOnBorrow, boolean testOnReturn,
0483:                    long timeBetweenEvictionRunsMillis,
0484:                    int numTestsPerEvictionRun,
0485:                    long minEvictableIdleTimeMillis, boolean testWhileIdle) {
0486:                _factory = factory;
0487:                _maxActive = maxActive;
0488:                switch (whenExhaustedAction) {
0489:                case WHEN_EXHAUSTED_BLOCK:
0490:                case WHEN_EXHAUSTED_FAIL:
0491:                case WHEN_EXHAUSTED_GROW:
0492:                    _whenExhaustedAction = whenExhaustedAction;
0493:                    break;
0494:                default:
0495:                    throw new IllegalArgumentException("whenExhaustedAction "
0496:                            + whenExhaustedAction + " not recognized.");
0497:                }
0498:                _maxWait = maxWait;
0499:                _maxIdle = maxIdle;
0500:                _maxTotal = maxTotal;
0501:                _minIdle = minIdle;
0502:                _testOnBorrow = testOnBorrow;
0503:                _testOnReturn = testOnReturn;
0504:                _timeBetweenEvictionRunsMillis = timeBetweenEvictionRunsMillis;
0505:                _numTestsPerEvictionRun = numTestsPerEvictionRun;
0506:                _minEvictableIdleTimeMillis = minEvictableIdleTimeMillis;
0507:                _testWhileIdle = testWhileIdle;
0508:
0509:                _poolMap = new HashMap();
0510:                _activeMap = new HashMap();
0511:
0512:                startEvictor(_timeBetweenEvictionRunsMillis);
0513:            }
0514:
0515:            //--- public methods ---------------------------------------------
0516:
0517:            //--- configuration methods --------------------------------------
0518:
0519:            /**
0520:             * Returns the cap on the number of active instances from my pool (per key).
0521:             * @return the cap on the number of active instances from my pool (per key).
0522:             * @see #setMaxActive
0523:             */
0524:            public synchronized int getMaxActive() {
0525:                return _maxActive;
0526:            }
0527:
0528:            /**
0529:             * Sets the cap on the number of active instances from my pool (per key).
0530:             * @param maxActive The cap on the number of active instances from my pool (per key).
0531:             *                  Use a negative value for an infinite number of instances.
0532:             * @see #getMaxActive
0533:             */
0534:            public synchronized void setMaxActive(int maxActive) {
0535:                _maxActive = maxActive;
0536:                notifyAll();
0537:            }
0538:
0539:            /**
0540:             * Returns the cap on the total number of instances from my pool if non-positive.
0541:             * @return the cap on the total number of instances from my pool if non-positive.
0542:             * @see #setMaxTotal
0543:             */
0544:            public synchronized int getMaxTotal() {
0545:                return _maxTotal;
0546:            }
0547:
0548:            /**
0549:             * Sets the cap on the total number of instances from my pool if non-positive.
0550:             * @param maxTotal The cap on the total number of instances from my pool.
0551:             *                  Use a non-positive value for an infinite number of instances.
0552:             * @see #getMaxTotal
0553:             */
0554:            public synchronized void setMaxTotal(int maxTotal) {
0555:                _maxTotal = maxTotal;
0556:                notifyAll();
0557:            }
0558:
0559:            /**
0560:             * Returns the action to take when the {@link #borrowObject} method
0561:             * is invoked when the pool is exhausted (the maximum number
0562:             * of "active" objects has been reached).
0563:             *
0564:             * @return one of {@link #WHEN_EXHAUSTED_BLOCK}, {@link #WHEN_EXHAUSTED_FAIL} or {@link #WHEN_EXHAUSTED_GROW}
0565:             * @see #setWhenExhaustedAction
0566:             */
0567:            public synchronized byte getWhenExhaustedAction() {
0568:                return _whenExhaustedAction;
0569:            }
0570:
0571:            /**
0572:             * Sets the action to take when the {@link #borrowObject} method
0573:             * is invoked when the pool is exhausted (the maximum number
0574:             * of "active" objects has been reached).
0575:             *
0576:             * @param whenExhaustedAction the action code, which must be one of
0577:             *        {@link #WHEN_EXHAUSTED_BLOCK}, {@link #WHEN_EXHAUSTED_FAIL},
0578:             *        or {@link #WHEN_EXHAUSTED_GROW}
0579:             * @see #getWhenExhaustedAction
0580:             */
0581:            public synchronized void setWhenExhaustedAction(
0582:                    byte whenExhaustedAction) {
0583:                switch (whenExhaustedAction) {
0584:                case WHEN_EXHAUSTED_BLOCK:
0585:                case WHEN_EXHAUSTED_FAIL:
0586:                case WHEN_EXHAUSTED_GROW:
0587:                    _whenExhaustedAction = whenExhaustedAction;
0588:                    notifyAll();
0589:                    break;
0590:                default:
0591:                    throw new IllegalArgumentException("whenExhaustedAction "
0592:                            + whenExhaustedAction + " not recognized.");
0593:                }
0594:            }
0595:
0596:            /**
0597:             * Returns the maximum amount of time (in milliseconds) the
0598:             * {@link #borrowObject} method should block before throwing
0599:             * an exception when the pool is exhausted and the
0600:             * {@link #setWhenExhaustedAction "when exhausted" action} is
0601:             * {@link #WHEN_EXHAUSTED_BLOCK}.
0602:             *
0603:             * When less than 0, the {@link #borrowObject} method
0604:             * may block indefinitely.
0605:             *
0606:             * @see #setMaxWait
0607:             * @see #setWhenExhaustedAction
0608:             * @see #WHEN_EXHAUSTED_BLOCK
0609:             */
0610:            public synchronized long getMaxWait() {
0611:                return _maxWait;
0612:            }
0613:
0614:            /**
0615:             * Sets the maximum amount of time (in milliseconds) the
0616:             * {@link #borrowObject} method should block before throwing
0617:             * an exception when the pool is exhausted and the
0618:             * {@link #setWhenExhaustedAction "when exhausted" action} is
0619:             * {@link #WHEN_EXHAUSTED_BLOCK}.
0620:             *
0621:             * When less than 0, the {@link #borrowObject} method
0622:             * may block indefinitely.
0623:             *
0624:             * @see #getMaxWait
0625:             * @see #setWhenExhaustedAction
0626:             * @see #WHEN_EXHAUSTED_BLOCK
0627:             */
0628:            public synchronized void setMaxWait(long maxWait) {
0629:                _maxWait = maxWait;
0630:            }
0631:
0632:            /**
0633:             * Returns the cap on the number of "idle" instances in the pool.
0634:             * @return the cap on the number of "idle" instances in the pool.
0635:             * @see #setMaxIdle
0636:             */
0637:            public synchronized int getMaxIdle() {
0638:                return _maxIdle;
0639:            }
0640:
0641:            /**
0642:             * Sets the cap on the number of "idle" instances in the pool.
0643:             * @param maxIdle The cap on the number of "idle" instances in the pool.
0644:             *                Use a negative value to indicate an unlimited number
0645:             *                of idle instances.
0646:             * @see #getMaxIdle
0647:             */
0648:            public synchronized void setMaxIdle(int maxIdle) {
0649:                _maxIdle = maxIdle;
0650:                notifyAll();
0651:            }
0652:
0653:            /**
0654:             * Sets the minimum number of idle objects in pool to maintain (per key)
0655:             * @param poolSize - The minimum size of the pool
0656:             * @see #getMinIdle
0657:             */
0658:            public synchronized void setMinIdle(int poolSize) {
0659:                _minIdle = poolSize;
0660:            }
0661:
0662:            /**
0663:             * Returns the minimum number of idle objects in pool to maintain (per key)
0664:             * @return the minimum number of idle objects in pool to maintain (per key)
0665:             * @see #setMinIdle
0666:             */
0667:            public synchronized int getMinIdle() {
0668:                return _minIdle;
0669:            }
0670:
0671:            /**
0672:             * When <tt>true</tt>, objects will be
0673:             * {@link org.apache.commons.pool.PoolableObjectFactory#validateObject validated}
0674:             * before being returned by the {@link #borrowObject}
0675:             * method.  If the object fails to validate,
0676:             * it will be dropped from the pool, and we will attempt
0677:             * to borrow another.
0678:             *
0679:             * @see #setTestOnBorrow
0680:             */
0681:            public synchronized boolean getTestOnBorrow() {
0682:                return _testOnBorrow;
0683:            }
0684:
0685:            /**
0686:             * When <tt>true</tt>, objects will be
0687:             * {@link org.apache.commons.pool.PoolableObjectFactory#validateObject validated}
0688:             * before being returned by the {@link #borrowObject}
0689:             * method.  If the object fails to validate,
0690:             * it will be dropped from the pool, and we will attempt
0691:             * to borrow another.
0692:             *
0693:             * @see #getTestOnBorrow
0694:             */
0695:            public synchronized void setTestOnBorrow(boolean testOnBorrow) {
0696:                _testOnBorrow = testOnBorrow;
0697:            }
0698:
0699:            /**
0700:             * When <tt>true</tt>, objects will be
0701:             * {@link org.apache.commons.pool.PoolableObjectFactory#validateObject validated}
0702:             * before being returned to the pool within the
0703:             * {@link #returnObject}.
0704:             *
0705:             * @see #setTestOnReturn
0706:             */
0707:            public synchronized boolean getTestOnReturn() {
0708:                return _testOnReturn;
0709:            }
0710:
0711:            /**
0712:             * When <tt>true</tt>, objects will be
0713:             * {@link org.apache.commons.pool.PoolableObjectFactory#validateObject validated}
0714:             * before being returned to the pool within the
0715:             * {@link #returnObject}.
0716:             *
0717:             * @see #getTestOnReturn
0718:             */
0719:            public synchronized void setTestOnReturn(boolean testOnReturn) {
0720:                _testOnReturn = testOnReturn;
0721:            }
0722:
0723:            /**
0724:             * Returns the number of milliseconds to sleep between runs of the
0725:             * idle object evictor thread.
0726:             * When non-positive, no idle object evictor thread will be
0727:             * run.
0728:             *
0729:             * @see #setTimeBetweenEvictionRunsMillis
0730:             */
0731:            public synchronized long getTimeBetweenEvictionRunsMillis() {
0732:                return _timeBetweenEvictionRunsMillis;
0733:            }
0734:
0735:            /**
0736:             * Sets the number of milliseconds to sleep between runs of the
0737:             * idle object evictor thread.
0738:             * When non-positive, no idle object evictor thread will be
0739:             * run.
0740:             *
0741:             * @see #getTimeBetweenEvictionRunsMillis
0742:             */
0743:            public synchronized void setTimeBetweenEvictionRunsMillis(
0744:                    long timeBetweenEvictionRunsMillis) {
0745:                _timeBetweenEvictionRunsMillis = timeBetweenEvictionRunsMillis;
0746:                startEvictor(_timeBetweenEvictionRunsMillis);
0747:            }
0748:
0749:            /**
0750:             * Returns the number of objects to examine during each run of the
0751:             * idle object evictor thread (if any).
0752:             *
0753:             * @see #setNumTestsPerEvictionRun
0754:             * @see #setTimeBetweenEvictionRunsMillis
0755:             */
0756:            public synchronized int getNumTestsPerEvictionRun() {
0757:                return _numTestsPerEvictionRun;
0758:            }
0759:
0760:            /**
0761:             * Sets the number of objects to examine during each run of the
0762:             * idle object evictor thread (if any).
0763:             * <p>
0764:             * When a negative value is supplied, <tt>ceil({@link #getNumIdle})/abs({@link #getNumTestsPerEvictionRun})</tt>
0765:             * tests will be run.  I.e., when the value is <i>-n</i>, roughly one <i>n</i>th of the
0766:             * idle objects will be tested per run.
0767:             *
0768:             * @see #getNumTestsPerEvictionRun
0769:             * @see #setTimeBetweenEvictionRunsMillis
0770:             */
0771:            public synchronized void setNumTestsPerEvictionRun(
0772:                    int numTestsPerEvictionRun) {
0773:                _numTestsPerEvictionRun = numTestsPerEvictionRun;
0774:            }
0775:
0776:            /**
0777:             * Returns the minimum amount of time an object may sit idle in the pool
0778:             * before it is eligable for eviction by the idle object evictor
0779:             * (if any).
0780:             *
0781:             * @see #setMinEvictableIdleTimeMillis
0782:             * @see #setTimeBetweenEvictionRunsMillis
0783:             */
0784:            public synchronized long getMinEvictableIdleTimeMillis() {
0785:                return _minEvictableIdleTimeMillis;
0786:            }
0787:
0788:            /**
0789:             * Sets the minimum amount of time an object may sit idle in the pool
0790:             * before it is eligable for eviction by the idle object evictor
0791:             * (if any).
0792:             * When non-positive, no objects will be evicted from the pool
0793:             * due to idle time alone.
0794:             *
0795:             * @see #getMinEvictableIdleTimeMillis
0796:             * @see #setTimeBetweenEvictionRunsMillis
0797:             */
0798:            public synchronized void setMinEvictableIdleTimeMillis(
0799:                    long minEvictableIdleTimeMillis) {
0800:                _minEvictableIdleTimeMillis = minEvictableIdleTimeMillis;
0801:            }
0802:
0803:            /**
0804:             * When <tt>true</tt>, objects will be
0805:             * {@link org.apache.commons.pool.PoolableObjectFactory#validateObject validated}
0806:             * by the idle object evictor (if any).  If an object
0807:             * fails to validate, it will be dropped from the pool.
0808:             *
0809:             * @see #setTestWhileIdle
0810:             * @see #setTimeBetweenEvictionRunsMillis
0811:             */
0812:            public synchronized boolean getTestWhileIdle() {
0813:                return _testWhileIdle;
0814:            }
0815:
0816:            /**
0817:             * When <tt>true</tt>, objects will be
0818:             * {@link org.apache.commons.pool.PoolableObjectFactory#validateObject validated}
0819:             * by the idle object evictor (if any).  If an object
0820:             * fails to validate, it will be dropped from the pool.
0821:             *
0822:             * @see #getTestWhileIdle
0823:             * @see #setTimeBetweenEvictionRunsMillis
0824:             */
0825:            public synchronized void setTestWhileIdle(boolean testWhileIdle) {
0826:                _testWhileIdle = testWhileIdle;
0827:            }
0828:
0829:            /**
0830:             * Sets my configuration.
0831:             * @see GenericKeyedObjectPool.Config
0832:             */
0833:            public synchronized void setConfig(
0834:                    GenericKeyedObjectPool.Config conf) {
0835:                setMaxIdle(conf.maxIdle);
0836:                setMaxActive(conf.maxActive);
0837:                setMaxTotal(conf.maxTotal);
0838:                setMinIdle(conf.minIdle);
0839:                setMaxWait(conf.maxWait);
0840:                setWhenExhaustedAction(conf.whenExhaustedAction);
0841:                setTestOnBorrow(conf.testOnBorrow);
0842:                setTestOnReturn(conf.testOnReturn);
0843:                setTestWhileIdle(conf.testWhileIdle);
0844:                setNumTestsPerEvictionRun(conf.numTestsPerEvictionRun);
0845:                setMinEvictableIdleTimeMillis(conf.minEvictableIdleTimeMillis);
0846:                setTimeBetweenEvictionRunsMillis(conf.timeBetweenEvictionRunsMillis);
0847:            }
0848:
0849:            //-- ObjectPool methods ------------------------------------------
0850:
0851:            public synchronized Object borrowObject(Object key)
0852:                    throws Exception {
0853:                long starttime = System.currentTimeMillis();
0854:                boolean newlyCreated = false;
0855:                for (;;) {
0856:                    LinkedList pool = (LinkedList) (_poolMap.get(key));
0857:                    if (null == pool) {
0858:                        pool = new LinkedList();
0859:                        _poolMap.put(key, pool);
0860:                    }
0861:                    ObjectTimestampPair pair = null;
0862:                    // if there are any sleeping, just grab one of those
0863:                    try {
0864:                        pair = (ObjectTimestampPair) (pool.removeFirst());
0865:                        if (null != pair) {
0866:                            _totalIdle--;
0867:                        }
0868:                    } catch (NoSuchElementException e) { /* ignored */
0869:                    }
0870:                    // otherwise
0871:                    if (null == pair) {
0872:                        // if there is a totalMaxActive and we are at the limit then
0873:                        // we have to make room
0874:                        if ((_maxTotal > 0)
0875:                                && (_totalActive + _totalIdle >= _maxTotal)) {
0876:                            clearOldest();
0877:                        }
0878:
0879:                        // check if we can create one
0880:                        // (note we know that the num sleeping is 0, else we wouldn't be here)
0881:                        int active = getActiveCount(key);
0882:                        if ((_maxActive < 0 || active < _maxActive)
0883:                                && (_maxTotal < 0 || _totalActive + _totalIdle < _maxTotal)) {
0884:                            Object obj = _factory.makeObject(key);
0885:                            pair = new ObjectTimestampPair(obj);
0886:                            newlyCreated = true;
0887:                        } else {
0888:                            // the pool is exhausted
0889:                            switch (_whenExhaustedAction) {
0890:                            case WHEN_EXHAUSTED_GROW:
0891:                                Object obj = _factory.makeObject(key);
0892:                                pair = new ObjectTimestampPair(obj);
0893:                                break;
0894:                            case WHEN_EXHAUSTED_FAIL:
0895:                                throw new NoSuchElementException();
0896:                            case WHEN_EXHAUSTED_BLOCK:
0897:                                try {
0898:                                    if (_maxWait <= 0) {
0899:                                        wait();
0900:                                    } else {
0901:                                        // this code may be executed again after a notify then continue cycle
0902:                                        // so, need to calculate the amount of time to wait
0903:                                        final long elapsed = (System
0904:                                                .currentTimeMillis() - starttime);
0905:                                        final long waitTime = _maxWait
0906:                                                - elapsed;
0907:                                        if (waitTime > 0) {
0908:                                            wait(waitTime);
0909:                                        }
0910:                                    }
0911:                                } catch (InterruptedException e) {
0912:                                    // ignored
0913:                                }
0914:                                if (_maxWait > 0
0915:                                        && ((System.currentTimeMillis() - starttime) >= _maxWait)) {
0916:                                    throw new NoSuchElementException(
0917:                                            "Timeout waiting for idle object");
0918:                                } else {
0919:                                    continue; // keep looping
0920:                                }
0921:                            default:
0922:                                throw new IllegalArgumentException(
0923:                                        "whenExhaustedAction "
0924:                                                + _whenExhaustedAction
0925:                                                + " not recognized.");
0926:                            }
0927:                        }
0928:                    }
0929:                    _factory.activateObject(key, pair.value);
0930:                    if (_testOnBorrow
0931:                            && !_factory.validateObject(key, pair.value)) {
0932:                        _factory.destroyObject(key, pair.value);
0933:                        if (newlyCreated) {
0934:                            throw new NoSuchElementException(
0935:                                    "Could not create a validated object");
0936:                        } // else keep looping
0937:                    } else {
0938:                        incrementActiveCount(key);
0939:                        return pair.value;
0940:                    }
0941:                }
0942:            }
0943:
0944:            public synchronized void clear() {
0945:                for (Iterator keyiter = _poolMap.keySet().iterator(); keyiter
0946:                        .hasNext();) {
0947:                    Object key = keyiter.next();
0948:                    final LinkedList list = (LinkedList) (_poolMap.get(key));
0949:                    for (Iterator it = list.iterator(); it.hasNext();) {
0950:                        try {
0951:                            _factory.destroyObject(key,
0952:                                    ((ObjectTimestampPair) (it.next())).value);
0953:                        } catch (Exception e) {
0954:                            // ignore error, keep destroying the rest
0955:                        }
0956:                        it.remove();
0957:                    }
0958:                }
0959:                _poolMap.clear();
0960:                if (_recentlyEvictedKeys != null) {
0961:                    _recentlyEvictedKeys.clear();
0962:                }
0963:                _totalIdle = 0;
0964:                notifyAll();
0965:            }
0966:
0967:            /**
0968:             * Method clears oldest 15% of objects in pool.  The method sorts the
0969:             * objects into a TreeMap and then iterates the first 15% for removal
0970:             */
0971:            public synchronized void clearOldest() {
0972:                // build sorted map of idle objects
0973:                TreeMap map = new TreeMap();
0974:                for (Iterator keyiter = _poolMap.keySet().iterator(); keyiter
0975:                        .hasNext();) {
0976:                    Object key = keyiter.next();
0977:                    LinkedList list = (LinkedList) _poolMap.get(key);
0978:                    for (Iterator it = list.iterator(); it.hasNext();) {
0979:                        // each item into the map uses the objectimestamppair object
0980:                        // as the key.  It then gets sorted based on the timstamp field
0981:                        // each value in the map is the parent list it belongs in.
0982:                        ObjectTimestampPair pair = (ObjectTimestampPair) it
0983:                                .next();
0984:                        map.put(pair, key);
0985:                    }
0986:                }
0987:
0988:                // Now iterate created map and kill the first 15% plus one to account for zero
0989:                Set setPairKeys = map.entrySet();
0990:                int itemsToRemove = ((int) (map.size() * 0.15)) + 1;
0991:
0992:                Iterator iter = setPairKeys.iterator();
0993:                while (iter.hasNext() && itemsToRemove > 0) {
0994:                    Map.Entry entry = (Map.Entry) iter.next();
0995:                    // kind of backwards on naming.  In the map, each key is the objecttimestamppair
0996:                    // because it has the ordering with the timestamp value.  Each value that the
0997:                    // key references is the key of the list it belongs to.
0998:                    Object key = entry.getValue();
0999:                    ObjectTimestampPair pairTimeStamp = (ObjectTimestampPair) entry
1000:                            .getKey();
1001:                    LinkedList list = (LinkedList) _poolMap.get(key);
1002:                    list.remove(pairTimeStamp);
1003:
1004:                    try {
1005:                        _factory.destroyObject(key, pairTimeStamp.value);
1006:                    } catch (Exception e) {
1007:                        // ignore error, keep destroying the rest
1008:                    }
1009:                    // if that was the last object for that key, drop that pool
1010:                    if (list.isEmpty()) {
1011:                        _poolMap.remove(key);
1012:                    }
1013:                    _totalIdle--;
1014:                    itemsToRemove--;
1015:                }
1016:                notifyAll();
1017:            }
1018:
1019:            public synchronized void clear(Object key) {
1020:                LinkedList pool = (LinkedList) (_poolMap.remove(key));
1021:                if (null == pool) {
1022:                    return;
1023:                } else {
1024:                    for (Iterator it = pool.iterator(); it.hasNext();) {
1025:                        try {
1026:                            _factory.destroyObject(key,
1027:                                    ((ObjectTimestampPair) (it.next())).value);
1028:                        } catch (Exception e) {
1029:                            // ignore error, keep destroying the rest
1030:                        }
1031:                        it.remove();
1032:                        _totalIdle--;
1033:                    }
1034:                }
1035:                notifyAll();
1036:            }
1037:
1038:            public synchronized int getNumActive() {
1039:                return _totalActive;
1040:            }
1041:
1042:            public synchronized int getNumIdle() {
1043:                return _totalIdle;
1044:            }
1045:
1046:            public synchronized int getNumActive(Object key) {
1047:                return getActiveCount(key);
1048:            }
1049:
1050:            public synchronized int getNumIdle(Object key) {
1051:                try {
1052:                    return ((LinkedList) (_poolMap.get(key))).size();
1053:                } catch (Exception e) {
1054:                    return 0;
1055:                }
1056:            }
1057:
1058:            public synchronized void returnObject(Object key, Object obj)
1059:                    throws Exception {
1060:
1061:                // if we need to validate this object, do so
1062:                boolean success = true; // whether or not this object passed validation
1063:                if (_testOnReturn && !_factory.validateObject(key, obj)) {
1064:                    success = false;
1065:                    try {
1066:                        _factory.destroyObject(key, obj);
1067:                    } catch (Exception e) {
1068:                        // ignored
1069:                    }
1070:                } else {
1071:                    try {
1072:                        _factory.passivateObject(key, obj);
1073:                    } catch (Exception e) {
1074:                        success = false;
1075:                    }
1076:                }
1077:
1078:                boolean shouldDestroy = false;
1079:                // grab the pool (list) of objects associated with the given key
1080:                LinkedList pool = (LinkedList) (_poolMap.get(key));
1081:                // if it doesn't exist, create it
1082:                if (null == pool) {
1083:                    pool = new LinkedList();
1084:                    _poolMap.put(key, pool);
1085:                }
1086:                decrementActiveCount(key);
1087:                // if there's no space in the pool, flag the object for destruction
1088:                // else if we passivated succesfully, return it to the pool
1089:                if (_maxIdle >= 0 && (pool.size() >= _maxIdle)) {
1090:                    shouldDestroy = true;
1091:                } else if (success) {
1092:                    pool.addLast(new ObjectTimestampPair(obj));
1093:                    _totalIdle++;
1094:                }
1095:                notifyAll();
1096:
1097:                if (shouldDestroy) {
1098:                    try {
1099:                        _factory.destroyObject(key, obj);
1100:                    } catch (Exception e) {
1101:                        // ignored?
1102:                    }
1103:                }
1104:            }
1105:
1106:            public synchronized void invalidateObject(Object key, Object obj)
1107:                    throws Exception {
1108:                try {
1109:                    _factory.destroyObject(key, obj);
1110:                } finally {
1111:                    decrementActiveCount(key);
1112:                    notifyAll(); // _totalActive has changed
1113:                }
1114:            }
1115:
1116:            public synchronized void addObject(Object key) throws Exception {
1117:                Object obj = _factory.makeObject(key);
1118:                incrementActiveCount(key); // returnObject will decrement this
1119:                returnObject(key, obj);
1120:            }
1121:
1122:            /**
1123:             * Registers a key for pool control.
1124:             *
1125:             * If <i>populateImmediately</i> is <code>true</code>, the pool will immediately commence
1126:             * a sustain cycle. If <i>populateImmediately</i> is <code>false</code>, the pool will be
1127:             * populated when the next schedules sustain task is run.
1128:             *
1129:             * @param key - The key to register for pool control.
1130:             * @param populateImmediately - If this is <code>true</code>, the pool
1131:             * will start a sustain cycle immediately.
1132:             */
1133:            public synchronized void preparePool(Object key,
1134:                    boolean populateImmediately) {
1135:                LinkedList pool = (LinkedList) (_poolMap.get(key));
1136:                if (null == pool) {
1137:                    pool = new LinkedList();
1138:                    _poolMap.put(key, pool);
1139:                }
1140:
1141:                if (populateImmediately) {
1142:                    try {
1143:                        // Create the pooled objects
1144:                        ensureMinIdle(key);
1145:                    } catch (Exception e) {
1146:                        //Do nothing
1147:                    }
1148:                }
1149:            }
1150:
1151:            public synchronized void close() throws Exception {
1152:                clear();
1153:                _poolMap = null;
1154:                _activeMap = null;
1155:                _recentlyEvictedKeys = null;
1156:                if (null != _evictor) {
1157:                    _evictor.cancel();
1158:                    _evictor = null;
1159:                }
1160:            }
1161:
1162:            public synchronized void setFactory(
1163:                    KeyedPoolableObjectFactory factory)
1164:                    throws IllegalStateException {
1165:                if (0 < getNumActive()) {
1166:                    throw new IllegalStateException(
1167:                            "Objects are already active");
1168:                } else {
1169:                    clear();
1170:                    _factory = factory;
1171:                }
1172:            }
1173:
1174:            public synchronized void evict() throws Exception {
1175:                Object key = null;
1176:                if (_recentlyEvictedKeys == null) {
1177:                    _recentlyEvictedKeys = new HashSet(_poolMap.size());
1178:                }
1179:                Set remainingKeys = new HashSet(_poolMap.keySet());
1180:                remainingKeys.removeAll(_recentlyEvictedKeys);
1181:                Iterator keyIter = remainingKeys.iterator();
1182:
1183:                ListIterator objIter = null;
1184:
1185:                for (int i = 0, m = getNumTests(); i < m; i++) {
1186:                    if (_poolMap.size() > 0) {
1187:                        // Find next idle object pool key to work on
1188:                        if (key == null) {
1189:                            if (!keyIter.hasNext()) {
1190:                                _recentlyEvictedKeys.clear();
1191:                                remainingKeys = new HashSet(_poolMap.keySet());
1192:                                keyIter = remainingKeys.iterator();
1193:                            }
1194:                            if (!keyIter.hasNext()) {
1195:                                // done, there are no keyed pools
1196:                                return;
1197:                            }
1198:                            key = keyIter.next();
1199:                        }
1200:
1201:                        // if we don't have a keyed object pool iterator
1202:                        if (objIter == null) {
1203:                            final LinkedList list = (LinkedList) _poolMap
1204:                                    .get(key);
1205:                            if (_evictLastIndex < 0
1206:                                    || _evictLastIndex > list.size()) {
1207:                                _evictLastIndex = list.size();
1208:                            }
1209:                            objIter = list.listIterator(_evictLastIndex);
1210:                        }
1211:
1212:                        // if the _evictionCursor has a previous object, then test it
1213:                        if (objIter.hasPrevious()) {
1214:                            ObjectTimestampPair pair = (ObjectTimestampPair) (objIter
1215:                                    .previous());
1216:                            boolean removeObject = false;
1217:                            if (_minEvictableIdleTimeMillis > 0
1218:                                    && System.currentTimeMillis() - pair.tstamp > _minEvictableIdleTimeMillis) {
1219:                                removeObject = true;
1220:                            }
1221:                            if (_testWhileIdle && removeObject == false) {
1222:                                boolean active = false;
1223:                                try {
1224:                                    _factory.activateObject(key, pair.value);
1225:                                    active = true;
1226:                                } catch (Exception e) {
1227:                                    removeObject = true;
1228:                                }
1229:                                if (active) {
1230:                                    if (!_factory.validateObject(key,
1231:                                            pair.value)) {
1232:                                        removeObject = true;
1233:                                    } else {
1234:                                        try {
1235:                                            _factory.passivateObject(key,
1236:                                                    pair.value);
1237:                                        } catch (Exception e) {
1238:                                            removeObject = true;
1239:                                        }
1240:                                    }
1241:                                }
1242:                            }
1243:                            if (removeObject) {
1244:                                try {
1245:                                    objIter.remove();
1246:                                    _totalIdle--;
1247:                                    _factory.destroyObject(key, pair.value);
1248:
1249:                                    // Do not remove the key from the _poolList or _poolmap, even if the list
1250:                                    // stored in the _poolMap for this key is empty when the
1251:                                    // {@link #getMinIdle <i>minIdle</i>} is > 0.
1252:                                    //
1253:                                    // Otherwise if it was the last object for that key, drop that pool
1254:                                    if ((_minIdle == 0)
1255:                                            && (((LinkedList) (_poolMap
1256:                                                    .get(key))).isEmpty())) {
1257:                                        _poolMap.remove(key);
1258:                                    }
1259:                                } catch (Exception e) {
1260:                                    ; // ignored
1261:                                }
1262:                            }
1263:                        } else {
1264:                            // else done evicting keyed pool
1265:                            _recentlyEvictedKeys.add(key);
1266:                            _evictLastIndex = -1;
1267:                            objIter = null;
1268:                        }
1269:                    }
1270:                }
1271:            }
1272:
1273:            /**
1274:             * Iterates through all the known keys and creates any necessary objects to maintain
1275:             * the minimum level of pooled objects.
1276:             * @see #getMinIdle
1277:             * @see #setMinIdle
1278:             * @throws Exception If there was an error whilst creating the pooled objects.
1279:             */
1280:            private synchronized void ensureMinIdle() throws Exception {
1281:                Iterator iterator = _poolMap.keySet().iterator();
1282:
1283:                //Check if should sustain the pool
1284:                if (_minIdle > 0) {
1285:                    // Loop through all elements in _poolList
1286:                    // Find out the total number of max active and max idle for that class
1287:                    // If the number is less than the minIdle, do creation loop to boost numbers
1288:                    // Increment idle count + 1
1289:                    while (iterator.hasNext()) {
1290:                        //Get the next key to process
1291:                        Object key = iterator.next();
1292:                        ensureMinIdle(key);
1293:                    }
1294:                }
1295:            }
1296:
1297:            /**
1298:             * Re-creates any needed objects to maintain the minimum levels of
1299:             * pooled objects for the specified key.
1300:             *
1301:             * This method uses {@link #calculateDefecit} to calculate the number
1302:             * of objects to be created. {@link #calculateDefecit} can be overridden to
1303:             * provide a different method of calculating the number of objects to be
1304:             * created.
1305:             * @param key The key to process
1306:             * @throws Exception If there was an error whilst creating the pooled objects
1307:             */
1308:            private synchronized void ensureMinIdle(Object key)
1309:                    throws Exception {
1310:                // Calculate current pool objects
1311:                int numberToCreate = calculateDefecit(key);
1312:
1313:                //Create required pool objects, if none to create, this loop will not be run.
1314:                for (int i = 0; i < numberToCreate; i++) {
1315:                    addObject(key);
1316:                }
1317:            }
1318:
1319:            //--- non-public methods ----------------------------------------
1320:
1321:            /**
1322:             * Start the eviction thread or service, or when
1323:             * <i>delay</i> is non-positive, stop it
1324:             * if it is already running.
1325:             */
1326:            protected synchronized void startEvictor(long delay) {
1327:                if (null != _evictor) {
1328:                    _evictor.cancel();
1329:                    _evictor = null;
1330:                }
1331:                if (delay > 0) {
1332:                    _evictor = new Evictor();
1333:                    GenericObjectPool.EVICTION_TIMER.schedule(_evictor, delay,
1334:                            delay);
1335:                }
1336:            }
1337:
1338:            synchronized String debugInfo() {
1339:                StringBuffer buf = new StringBuffer();
1340:                buf.append("Active: ").append(getNumActive()).append("\n");
1341:                buf.append("Idle: ").append(getNumIdle()).append("\n");
1342:                Iterator it = _poolMap.keySet().iterator();
1343:                while (it.hasNext()) {
1344:                    buf.append("\t").append(_poolMap.get(it.next())).append(
1345:                            "\n");
1346:                }
1347:                return buf.toString();
1348:            }
1349:
1350:            private int getNumTests() {
1351:                if (_numTestsPerEvictionRun >= 0) {
1352:                    return _numTestsPerEvictionRun;
1353:                } else {
1354:                    return (int) (Math.ceil((double) _totalIdle
1355:                            / Math.abs((double) _numTestsPerEvictionRun)));
1356:                }
1357:            }
1358:
1359:            private void incrementActiveCount(Object key) {
1360:                _totalActive++;
1361:                Integer active = (Integer) (_activeMap.get(key));
1362:                if (null == active) {
1363:                    _activeMap.put(key, new Integer(1));
1364:                } else {
1365:                    _activeMap.put(key, new Integer(active.intValue() + 1));
1366:                }
1367:            }
1368:
1369:            private void decrementActiveCount(Object key) {
1370:                _totalActive--;
1371:                Integer active = (Integer) (_activeMap.get(key));
1372:                if (null == active) {
1373:                    // do nothing, either null or zero is OK
1374:                } else if (active.intValue() <= 1) {
1375:                    _activeMap.remove(key);
1376:                } else {
1377:                    _activeMap.put(key, new Integer(active.intValue() - 1));
1378:                }
1379:            }
1380:
1381:            private int getActiveCount(Object key) {
1382:                int active = 0;
1383:                Integer act = (Integer) (_activeMap.get(key));
1384:                if (null != act) {
1385:                    active = act.intValue();
1386:                }
1387:                return active;
1388:            }
1389:
1390:            /**
1391:             * This returns the number of objects to create during the pool
1392:             * sustain cycle. This will ensure that the minimum number of idle
1393:             * connections is maintained without going past the maxPool value.
1394:             * <p>
1395:             * This method has been left public so derived classes can override
1396:             * the way the defecit is calculated. ie... Increase/decrease the pool
1397:             * size at certain times of day to accomodate for usage patterns.
1398:             *
1399:             * @param key - The key of the pool to calculate the number of
1400:             *              objects to be re-created
1401:             * @return The number of objects to be created
1402:             */
1403:            private int calculateDefecit(Object key) {
1404:                int objectDefecit = 0;
1405:
1406:                //Calculate no of objects needed to be created, in order to have
1407:                //the number of pooled objects < maxActive();
1408:                objectDefecit = getMinIdle() - getNumIdle(key);
1409:                if (getMaxActive() > 0) {
1410:                    int growLimit = Math.max(0, getMaxActive()
1411:                            - getNumActive(key) - getNumIdle(key));
1412:                    objectDefecit = Math.min(objectDefecit, growLimit);
1413:                }
1414:
1415:                // Take the maxTotal limit into account
1416:                if (getMaxTotal() > 0) {
1417:                    int growLimit = Math.max(0, getMaxTotal() - getNumActive()
1418:                            - getNumIdle());
1419:                    objectDefecit = Math.min(objectDefecit, growLimit);
1420:                }
1421:
1422:                return objectDefecit;
1423:            }
1424:
1425:            //--- inner classes ----------------------------------------------
1426:
1427:            /**
1428:             * A simple "struct" encapsulating an object instance and a timestamp.
1429:             *
1430:             * Implements Comparable, objects are sorted from old to new.
1431:             *
1432:             * This is also used by {@link GenericObjectPool}.
1433:             */
1434:            static class ObjectTimestampPair implements  Comparable {
1435:                Object value;
1436:                long tstamp;
1437:
1438:                ObjectTimestampPair(Object val) {
1439:                    this (val, System.currentTimeMillis());
1440:                }
1441:
1442:                ObjectTimestampPair(Object val, long time) {
1443:                    value = val;
1444:                    tstamp = time;
1445:                }
1446:
1447:                public String toString() {
1448:                    return value + ";" + tstamp;
1449:                }
1450:
1451:                public int compareTo(Object obj) {
1452:                    return compareTo((ObjectTimestampPair) obj);
1453:                }
1454:
1455:                public int compareTo(ObjectTimestampPair other) {
1456:                    return (int) (this .tstamp - other.tstamp);
1457:                }
1458:            }
1459:
1460:            /**
1461:             * The idle object evictor {@link TimerTask}.
1462:             * @see GenericKeyedObjectPool#setTimeBetweenEvictionRunsMillis
1463:             */
1464:            private class Evictor extends TimerTask {
1465:                public void run() {
1466:                    //Evict from the pool
1467:                    try {
1468:                        evict();
1469:                    } catch (Exception e) {
1470:                        // ignored
1471:                    }
1472:                    //Re-create the connections.
1473:                    try {
1474:                        ensureMinIdle();
1475:                    } catch (Exception e) {
1476:                        // ignored
1477:                    }
1478:                }
1479:            }
1480:
1481:            /**
1482:             * A simple "struct" encapsulating the
1483:             * configuration information for a {@link GenericKeyedObjectPool}.
1484:             * @see GenericKeyedObjectPool#GenericKeyedObjectPool(KeyedPoolableObjectFactory,GenericKeyedObjectPool.Config)
1485:             * @see GenericKeyedObjectPool#setConfig
1486:             */
1487:            public static class Config {
1488:                public int maxIdle = GenericKeyedObjectPool.DEFAULT_MAX_IDLE;
1489:                public int maxActive = GenericKeyedObjectPool.DEFAULT_MAX_ACTIVE;
1490:                public int maxTotal = GenericKeyedObjectPool.DEFAULT_MAX_TOTAL;
1491:                public int minIdle = GenericKeyedObjectPool.DEFAULT_MIN_IDLE;
1492:                public long maxWait = GenericKeyedObjectPool.DEFAULT_MAX_WAIT;
1493:                public byte whenExhaustedAction = GenericKeyedObjectPool.DEFAULT_WHEN_EXHAUSTED_ACTION;
1494:                public boolean testOnBorrow = GenericKeyedObjectPool.DEFAULT_TEST_ON_BORROW;
1495:                public boolean testOnReturn = GenericKeyedObjectPool.DEFAULT_TEST_ON_RETURN;
1496:                public boolean testWhileIdle = GenericKeyedObjectPool.DEFAULT_TEST_WHILE_IDLE;
1497:                public long timeBetweenEvictionRunsMillis = GenericKeyedObjectPool.DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS;
1498:                public int numTestsPerEvictionRun = GenericKeyedObjectPool.DEFAULT_NUM_TESTS_PER_EVICTION_RUN;
1499:                public long minEvictableIdleTimeMillis = GenericKeyedObjectPool.DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS;
1500:            }
1501:
1502:            //--- protected attributes ---------------------------------------
1503:
1504:            /**
1505:             * The cap on the number of idle instances in the pool (per key).
1506:             * @see #setMaxIdle
1507:             * @see #getMaxIdle
1508:             */
1509:            private int _maxIdle = DEFAULT_MAX_IDLE;
1510:
1511:            /**
1512:             * The minimum no of idle objects to keep in the pool (per key)
1513:             * @see #setMinIdle
1514:             * @see #getMinIdle
1515:             */
1516:            private int _minIdle = DEFAULT_MIN_IDLE;
1517:
1518:            /**
1519:             * The cap on the number of active instances from the pool (per key).
1520:             * @see #setMaxActive
1521:             * @see #getMaxActive
1522:             */
1523:            private int _maxActive = DEFAULT_MAX_ACTIVE;
1524:
1525:            /**
1526:             * The cap on the total number of instances from the pool if non-positive.
1527:             * @see #setMaxTotal
1528:             * @see #getMaxTotal
1529:             */
1530:            private int _maxTotal = DEFAULT_MAX_TOTAL;
1531:
1532:            /**
1533:             * The maximum amount of time (in millis) the
1534:             * {@link #borrowObject} method should block before throwing
1535:             * an exception when the pool is exhausted and the
1536:             * {@link #getWhenExhaustedAction "when exhausted" action} is
1537:             * {@link #WHEN_EXHAUSTED_BLOCK}.
1538:             *
1539:             * When less than 0, the {@link #borrowObject} method
1540:             * may block indefinitely.
1541:             *
1542:             * @see #setMaxWait
1543:             * @see #getMaxWait
1544:             * @see #WHEN_EXHAUSTED_BLOCK
1545:             * @see #setWhenExhaustedAction
1546:             * @see #getWhenExhaustedAction
1547:             */
1548:            private long _maxWait = DEFAULT_MAX_WAIT;
1549:
1550:            /**
1551:             * The action to take when the {@link #borrowObject} method
1552:             * is invoked when the pool is exhausted (the maximum number
1553:             * of "active" objects has been reached).
1554:             *
1555:             * @see #WHEN_EXHAUSTED_BLOCK
1556:             * @see #WHEN_EXHAUSTED_FAIL
1557:             * @see #WHEN_EXHAUSTED_GROW
1558:             * @see #DEFAULT_WHEN_EXHAUSTED_ACTION
1559:             * @see #setWhenExhaustedAction
1560:             * @see #getWhenExhaustedAction
1561:             */
1562:            private byte _whenExhaustedAction = DEFAULT_WHEN_EXHAUSTED_ACTION;
1563:
1564:            /**
1565:             * When <tt>true</tt>, objects will be
1566:             * {@link org.apache.commons.pool.PoolableObjectFactory#validateObject validated}
1567:             * before being returned by the {@link #borrowObject}
1568:             * method.  If the object fails to validate,
1569:             * it will be dropped from the pool, and we will attempt
1570:             * to borrow another.
1571:             *
1572:             * @see #setTestOnBorrow
1573:             * @see #getTestOnBorrow
1574:             */
1575:            private boolean _testOnBorrow = DEFAULT_TEST_ON_BORROW;
1576:
1577:            /**
1578:             * When <tt>true</tt>, objects will be
1579:             * {@link org.apache.commons.pool.PoolableObjectFactory#validateObject validated}
1580:             * before being returned to the pool within the
1581:             * {@link #returnObject}.
1582:             *
1583:             * @see #getTestOnReturn
1584:             * @see #setTestOnReturn
1585:             */
1586:            private boolean _testOnReturn = DEFAULT_TEST_ON_RETURN;
1587:
1588:            /**
1589:             * When <tt>true</tt>, objects will be
1590:             * {@link org.apache.commons.pool.PoolableObjectFactory#validateObject validated}
1591:             * by the idle object evictor (if any).  If an object
1592:             * fails to validate, it will be dropped from the pool.
1593:             *
1594:             * @see #setTestWhileIdle
1595:             * @see #getTestWhileIdle
1596:             * @see #getTimeBetweenEvictionRunsMillis
1597:             * @see #setTimeBetweenEvictionRunsMillis
1598:             */
1599:            private boolean _testWhileIdle = DEFAULT_TEST_WHILE_IDLE;
1600:
1601:            /**
1602:             * The number of milliseconds to sleep between runs of the
1603:             * idle object evictor thread.
1604:             * When non-positive, no idle object evictor thread will be
1605:             * run.
1606:             *
1607:             * @see #setTimeBetweenEvictionRunsMillis
1608:             * @see #getTimeBetweenEvictionRunsMillis
1609:             */
1610:            private long _timeBetweenEvictionRunsMillis = DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS;
1611:
1612:            /**
1613:             * The number of objects to examine during each run of the
1614:             * idle object evictor thread (if any).
1615:             * <p>
1616:             * When a negative value is supplied, <tt>ceil({@link #getNumIdle})/abs({@link #getNumTestsPerEvictionRun})</tt>
1617:             * tests will be run.  I.e., when the value is <i>-n</i>, roughly one <i>n</i>th of the
1618:             * idle objects will be tested per run.
1619:             *
1620:             * @see #setNumTestsPerEvictionRun
1621:             * @see #getNumTestsPerEvictionRun
1622:             * @see #getTimeBetweenEvictionRunsMillis
1623:             * @see #setTimeBetweenEvictionRunsMillis
1624:             */
1625:            private int _numTestsPerEvictionRun = DEFAULT_NUM_TESTS_PER_EVICTION_RUN;
1626:
1627:            /**
1628:             * The minimum amount of time an object may sit idle in the pool
1629:             * before it is eligable for eviction by the idle object evictor
1630:             * (if any).
1631:             * When non-positive, no objects will be evicted from the pool
1632:             * due to idle time alone.
1633:             *
1634:             * @see #setMinEvictableIdleTimeMillis
1635:             * @see #getMinEvictableIdleTimeMillis
1636:             * @see #getTimeBetweenEvictionRunsMillis
1637:             * @see #setTimeBetweenEvictionRunsMillis
1638:             */
1639:            private long _minEvictableIdleTimeMillis = DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS;
1640:
1641:            /** My hash of pools (CursorableLinkedLists). */
1642:            private HashMap _poolMap = null;
1643:
1644:            /** Count of active objects, per key. */
1645:            private HashMap _activeMap = null;
1646:
1647:            /** The total number of active instances. */
1648:            private int _totalActive = 0;
1649:
1650:            /** The total number of idle instances. */
1651:            private int _totalIdle = 0;
1652:
1653:            /** My {@link KeyedPoolableObjectFactory}. */
1654:            private KeyedPoolableObjectFactory _factory = null;
1655:
1656:            /**
1657:             * My idle object eviction {@link TimerTask}, if any.
1658:             */
1659:            private Evictor _evictor = null;
1660:
1661:            /**
1662:             * Idle object pool keys that have been evicted recently.
1663:             */
1664:            private Set _recentlyEvictedKeys = null;
1665:
1666:            /**
1667:             * Position in the _pool where the _evictor last stopped.
1668:             */
1669:            private int _evictLastIndex = -1;
1670:        }
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.