Source Code Cross Referenced for GenericObjectPool.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 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.Iterator;
0020:        import java.util.NoSuchElementException;
0021:        import java.util.LinkedList;
0022:        import java.util.ListIterator;
0023:        import java.util.Timer;
0024:        import java.util.TimerTask;
0025:
0026:        import org.apache.commons.pool.BaseObjectPool;
0027:        import org.apache.commons.pool.ObjectPool;
0028:        import org.apache.commons.pool.PoolableObjectFactory;
0029:        import org.apache.commons.pool.impl.GenericKeyedObjectPool.ObjectTimestampPair;
0030:
0031:        /**
0032:         * A configurable {@link ObjectPool} implementation.
0033:         * <p>
0034:         * When coupled with the appropriate {@link PoolableObjectFactory},
0035:         * <tt>GenericObjectPool</tt> provides robust pooling functionality for
0036:         * arbitrary objects.
0037:         * <p>
0038:         * A <tt>GenericObjectPool</tt> provides a number of configurable parameters:
0039:         * <ul>
0040:         *  <li>
0041:         *    {@link #setMaxActive <i>maxActive</i>} controls the maximum number of objects that can
0042:         *    be borrowed from the pool at one time.  When non-positive, there
0043:         *    is no limit to the number of objects that may be active at one time.
0044:         *    When {@link #setMaxActive <i>maxActive</i>} is exceeded, the pool is said to be exhausted.
0045:         *  </li>
0046:         *  <li>
0047:         *    {@link #setMaxIdle <i>maxIdle</i>} controls the maximum number of objects that can
0048:         *    sit idle in the pool at any time.  When negative, there
0049:         *    is no limit to the number of objects that may be idle at one time.
0050:         *  </li>
0051:         *  <li>
0052:         *    {@link #setWhenExhaustedAction <i>whenExhaustedAction</i>} specifies the
0053:         *    behaviour of the {@link #borrowObject} method when the pool is exhausted:
0054:         *    <ul>
0055:         *    <li>
0056:         *      When {@link #setWhenExhaustedAction <i>whenExhaustedAction</i>} is
0057:         *      {@link #WHEN_EXHAUSTED_FAIL}, {@link #borrowObject} will throw
0058:         *      a {@link NoSuchElementException}
0059:         *    </li>
0060:         *    <li>
0061:         *      When {@link #setWhenExhaustedAction <i>whenExhaustedAction</i>} is
0062:         *      {@link #WHEN_EXHAUSTED_GROW}, {@link #borrowObject} will create a new
0063:         *      object and return it(essentially making {@link #setMaxActive <i>maxActive</i>}
0064:         *      meaningless.)
0065:         *    </li>
0066:         *    <li>
0067:         *      When {@link #setWhenExhaustedAction <i>whenExhaustedAction</i>}
0068:         *      is {@link #WHEN_EXHAUSTED_BLOCK}, {@link #borrowObject} will block
0069:         *      (invoke {@link Object#wait} until a new or idle object is available.
0070:         *      If a positive {@link #setMaxWait <i>maxWait</i>}
0071:         *      value is supplied, the {@link #borrowObject} will block for at
0072:         *      most that many milliseconds, after which a {@link NoSuchElementException}
0073:         *      will be thrown.  If {@link #setMaxWait <i>maxWait</i>} is non-positive,
0074:         *      the {@link #borrowObject} method will block indefinitely.
0075:         *    </li>
0076:         *    </ul>
0077:         *  </li>
0078:         *  <li>
0079:         *    When {@link #setTestOnBorrow <i>testOnBorrow</i>} is set, the pool will
0080:         *    attempt to validate each object before it is returned from the
0081:         *    {@link #borrowObject} method. (Using the provided factory's
0082:         *    {@link PoolableObjectFactory#validateObject} method.)  Objects that fail
0083:         *    to validate will be dropped from the pool, and a different object will
0084:         *    be borrowed.
0085:         *  </li>
0086:         *  <li>
0087:         *    When {@link #setTestOnReturn <i>testOnReturn</i>} is set, the pool will
0088:         *    attempt to validate each object before it is returned to the pool in the
0089:         *    {@link #returnObject} method. (Using the provided factory's
0090:         *    {@link PoolableObjectFactory#validateObject}
0091:         *    method.)  Objects that fail to validate will be dropped from the pool.
0092:         *  </li>
0093:         * </ul>
0094:         * <p>
0095:         * Optionally, one may configure the pool to examine and possibly evict objects as they
0096:         * sit idle in the pool.  This is performed by an "idle object eviction" thread, which
0097:         * runs asychronously.  The idle object eviction thread may be configured using the
0098:         * following attributes:
0099:         * <ul>
0100:         *  <li>
0101:         *   {@link #setTimeBetweenEvictionRunsMillis <i>timeBetweenEvictionRunsMillis</i>}
0102:         *   indicates how long the eviction thread should sleep before "runs" of examining
0103:         *   idle objects.  When non-positive, no eviction thread will be launched.
0104:         *  </li>
0105:         *  <li>
0106:         *   {@link #setMinEvictableIdleTimeMillis <i>minEvictableIdleTimeMillis</i>}
0107:         *   specifies the minimum amount of time that an object may sit idle in the pool
0108:         *   before it is eligable for eviction due to idle time.  When non-positive, no object
0109:         *   will be dropped from the pool due to idle time alone.
0110:         *  </li>
0111:         *  <li>
0112:         *   {@link #setTestWhileIdle <i>testWhileIdle</i>} indicates whether or not idle
0113:         *   objects should be validated using the factory's
0114:         *   {@link PoolableObjectFactory#validateObject} method.  Objects
0115:         *   that fail to validate will be dropped from the pool.
0116:         *  </li>
0117:         * </ul>
0118:         * <p>
0119:         * GenericObjectPool is not usable without a {@link PoolableObjectFactory}.  A
0120:         * non-<code>null</code> factory must be provided either as a constructor argument
0121:         * or via a call to {@link #setFactory} before the pool is used.
0122:         *
0123:         * @see GenericKeyedObjectPool
0124:         * @author Rodney Waldhoff
0125:         * @author Dirk Verbeeck
0126:         * @version $Revision: 390563 $ $Date: 2006-03-31 20:28:14 -0500 (Fri, 31 Mar 2006) $
0127:         */
0128:        public class GenericObjectPool extends BaseObjectPool implements 
0129:                ObjectPool {
0130:
0131:            //--- public constants -------------------------------------------
0132:
0133:            /**
0134:             * A "when exhausted action" type indicating that when the pool is
0135:             * exhausted (i.e., the maximum number of active objects has
0136:             * been reached), the {@link #borrowObject}
0137:             * method should fail, throwing a {@link NoSuchElementException}.
0138:             * @see #WHEN_EXHAUSTED_BLOCK
0139:             * @see #WHEN_EXHAUSTED_GROW
0140:             * @see #setWhenExhaustedAction
0141:             */
0142:            public static final byte WHEN_EXHAUSTED_FAIL = 0;
0143:
0144:            /**
0145:             * A "when exhausted action" type indicating that when the pool
0146:             * is exhausted (i.e., the maximum number
0147:             * of active objects has been reached), the {@link #borrowObject}
0148:             * method should block until a new object is available, or the
0149:             * {@link #getMaxWait maximum wait time} has been reached.
0150:             * @see #WHEN_EXHAUSTED_FAIL
0151:             * @see #WHEN_EXHAUSTED_GROW
0152:             * @see #setMaxWait
0153:             * @see #getMaxWait
0154:             * @see #setWhenExhaustedAction
0155:             */
0156:            public static final byte WHEN_EXHAUSTED_BLOCK = 1;
0157:
0158:            /**
0159:             * A "when exhausted action" type indicating that when the pool is
0160:             * exhausted (i.e., the maximum number
0161:             * of active objects has been reached), the {@link #borrowObject}
0162:             * method should simply create a new object anyway.
0163:             * @see #WHEN_EXHAUSTED_FAIL
0164:             * @see #WHEN_EXHAUSTED_GROW
0165:             * @see #setWhenExhaustedAction
0166:             */
0167:            public static final byte WHEN_EXHAUSTED_GROW = 2;
0168:
0169:            /**
0170:             * The default cap on the number of "sleeping" instances in the pool.
0171:             * @see #getMaxIdle
0172:             * @see #setMaxIdle
0173:             */
0174:            public static final int DEFAULT_MAX_IDLE = 8;
0175:
0176:            /**
0177:             * The default minimum number of "sleeping" instances in the pool
0178:             * before before the evictor thread (if active) spawns new objects.
0179:             * @see #getMinIdle
0180:             * @see #setMinIdle
0181:             */
0182:            public static final int DEFAULT_MIN_IDLE = 0;
0183:
0184:            /**
0185:             * The default cap on the total number of active instances from the pool.
0186:             * @see #getMaxActive
0187:             */
0188:            public static final int DEFAULT_MAX_ACTIVE = 8;
0189:
0190:            /**
0191:             * The default "when exhausted action" for the pool.
0192:             * @see #WHEN_EXHAUSTED_BLOCK
0193:             * @see #WHEN_EXHAUSTED_FAIL
0194:             * @see #WHEN_EXHAUSTED_GROW
0195:             * @see #setWhenExhaustedAction
0196:             */
0197:            public static final byte DEFAULT_WHEN_EXHAUSTED_ACTION = WHEN_EXHAUSTED_BLOCK;
0198:
0199:            /**
0200:             * The default maximum amount of time (in millis) the
0201:             * {@link #borrowObject} method should block before throwing
0202:             * an exception when the pool is exhausted and the
0203:             * {@link #getWhenExhaustedAction "when exhausted" action} is
0204:             * {@link #WHEN_EXHAUSTED_BLOCK}.
0205:             * @see #getMaxWait
0206:             * @see #setMaxWait
0207:             */
0208:            public static final long DEFAULT_MAX_WAIT = -1L;
0209:
0210:            /**
0211:             * The default "test on borrow" value.
0212:             * @see #getTestOnBorrow
0213:             * @see #setTestOnBorrow
0214:             */
0215:            public static final boolean DEFAULT_TEST_ON_BORROW = false;
0216:
0217:            /**
0218:             * The default "test on return" value.
0219:             * @see #getTestOnReturn
0220:             * @see #setTestOnReturn
0221:             */
0222:            public static final boolean DEFAULT_TEST_ON_RETURN = false;
0223:
0224:            /**
0225:             * The default "test while idle" value.
0226:             * @see #getTestWhileIdle
0227:             * @see #setTestWhileIdle
0228:             * @see #getTimeBetweenEvictionRunsMillis
0229:             * @see #setTimeBetweenEvictionRunsMillis
0230:             */
0231:            public static final boolean DEFAULT_TEST_WHILE_IDLE = false;
0232:
0233:            /**
0234:             * The default "time between eviction runs" value.
0235:             * @see #getTimeBetweenEvictionRunsMillis
0236:             * @see #setTimeBetweenEvictionRunsMillis
0237:             */
0238:            public static final long DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS = -1L;
0239:
0240:            /**
0241:             * The default number of objects to examine per run in the
0242:             * idle object evictor.
0243:             * @see #getNumTestsPerEvictionRun
0244:             * @see #setNumTestsPerEvictionRun
0245:             * @see #getTimeBetweenEvictionRunsMillis
0246:             * @see #setTimeBetweenEvictionRunsMillis
0247:             */
0248:            public static final int DEFAULT_NUM_TESTS_PER_EVICTION_RUN = 3;
0249:
0250:            /**
0251:             * The default value for {@link #getMinEvictableIdleTimeMillis}.
0252:             * @see #getMinEvictableIdleTimeMillis
0253:             * @see #setMinEvictableIdleTimeMillis
0254:             */
0255:            public static final long DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS = 1000L * 60L * 30L;
0256:
0257:            /**
0258:             * The default value for {@link #getSoftMinEvictableIdleTimeMillis}.
0259:             * @see #getSoftMinEvictableIdleTimeMillis
0260:             * @see #setSoftMinEvictableIdleTimeMillis
0261:             */
0262:            public static final long DEFAULT_SOFT_MIN_EVICTABLE_IDLE_TIME_MILLIS = -1;
0263:
0264:            //--- package constants -------------------------------------------
0265:
0266:            /**
0267:             * Idle object evition Timer. Shared between all {@link GenericObjectPool}s and {@link GenericKeyedObjectPool} s.
0268:             */
0269:            static final Timer EVICTION_TIMER = new Timer(true);
0270:
0271:            //--- constructors -----------------------------------------------
0272:
0273:            /**
0274:             * Create a new <tt>GenericObjectPool</tt>.
0275:             */
0276:            public GenericObjectPool() {
0277:                this (null, DEFAULT_MAX_ACTIVE, DEFAULT_WHEN_EXHAUSTED_ACTION,
0278:                        DEFAULT_MAX_WAIT, DEFAULT_MAX_IDLE, DEFAULT_MIN_IDLE,
0279:                        DEFAULT_TEST_ON_BORROW, DEFAULT_TEST_ON_RETURN,
0280:                        DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS,
0281:                        DEFAULT_NUM_TESTS_PER_EVICTION_RUN,
0282:                        DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS,
0283:                        DEFAULT_TEST_WHILE_IDLE);
0284:            }
0285:
0286:            /**
0287:             * Create a new <tt>GenericObjectPool</tt> using the specified values.
0288:             * @param factory the (possibly <tt>null</tt>)PoolableObjectFactory to use to create, validate and destroy objects
0289:             */
0290:            public GenericObjectPool(PoolableObjectFactory factory) {
0291:                this (factory, DEFAULT_MAX_ACTIVE,
0292:                        DEFAULT_WHEN_EXHAUSTED_ACTION, DEFAULT_MAX_WAIT,
0293:                        DEFAULT_MAX_IDLE, DEFAULT_MIN_IDLE,
0294:                        DEFAULT_TEST_ON_BORROW, DEFAULT_TEST_ON_RETURN,
0295:                        DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS,
0296:                        DEFAULT_NUM_TESTS_PER_EVICTION_RUN,
0297:                        DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS,
0298:                        DEFAULT_TEST_WHILE_IDLE);
0299:            }
0300:
0301:            /**
0302:             * Create a new <tt>GenericObjectPool</tt> using the specified values.
0303:             * @param factory the (possibly <tt>null</tt>)PoolableObjectFactory to use to create, validate and destroy objects
0304:             * @param config a non-<tt>null</tt> {@link GenericObjectPool.Config} describing my configuration
0305:             */
0306:            public GenericObjectPool(PoolableObjectFactory factory,
0307:                    GenericObjectPool.Config config) {
0308:                this (factory, config.maxActive, config.whenExhaustedAction,
0309:                        config.maxWait, config.maxIdle, config.minIdle,
0310:                        config.testOnBorrow, config.testOnReturn,
0311:                        config.timeBetweenEvictionRunsMillis,
0312:                        config.numTestsPerEvictionRun,
0313:                        config.minEvictableIdleTimeMillis, config.testWhileIdle);
0314:            }
0315:
0316:            /**
0317:             * Create a new <tt>GenericObjectPool</tt> using the specified values.
0318:             * @param factory the (possibly <tt>null</tt>)PoolableObjectFactory to use to create, validate and destroy objects
0319:             * @param maxActive the maximum number of objects that can be borrowed from me at one time (see {@link #setMaxActive})
0320:             */
0321:            public GenericObjectPool(PoolableObjectFactory factory,
0322:                    int maxActive) {
0323:                this (factory, maxActive, DEFAULT_WHEN_EXHAUSTED_ACTION,
0324:                        DEFAULT_MAX_WAIT, DEFAULT_MAX_IDLE, DEFAULT_MIN_IDLE,
0325:                        DEFAULT_TEST_ON_BORROW, DEFAULT_TEST_ON_RETURN,
0326:                        DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS,
0327:                        DEFAULT_NUM_TESTS_PER_EVICTION_RUN,
0328:                        DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS,
0329:                        DEFAULT_TEST_WHILE_IDLE);
0330:            }
0331:
0332:            /**
0333:             * Create a new <tt>GenericObjectPool</tt> using the specified values.
0334:             * @param factory the (possibly <tt>null</tt>)PoolableObjectFactory to use to create, validate and destroy objects
0335:             * @param maxActive the maximum number of objects that can be borrowed from me at one time (see {@link #setMaxActive})
0336:             * @param whenExhaustedAction the action to take when the pool is exhausted (see {@link #getWhenExhaustedAction})
0337:             * @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})
0338:             */
0339:            public GenericObjectPool(PoolableObjectFactory factory,
0340:                    int maxActive, byte whenExhaustedAction, long maxWait) {
0341:                this (factory, maxActive, whenExhaustedAction, maxWait,
0342:                        DEFAULT_MAX_IDLE, DEFAULT_MIN_IDLE,
0343:                        DEFAULT_TEST_ON_BORROW, DEFAULT_TEST_ON_RETURN,
0344:                        DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS,
0345:                        DEFAULT_NUM_TESTS_PER_EVICTION_RUN,
0346:                        DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS,
0347:                        DEFAULT_TEST_WHILE_IDLE);
0348:            }
0349:
0350:            /**
0351:             * Create a new <tt>GenericObjectPool</tt> using the specified values.
0352:             * @param factory the (possibly <tt>null</tt>)PoolableObjectFactory to use to create, validate and destroy objects
0353:             * @param maxActive the maximum number of objects that can be borrowed from me at one time (see {@link #setMaxActive})
0354:             * @param whenExhaustedAction the action to take when the pool is exhausted (see {@link #getWhenExhaustedAction})
0355:             * @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})
0356:             * @param testOnBorrow whether or not to validate objects before they are returned by the {@link #borrowObject} method (see {@link #getTestOnBorrow})
0357:             * @param testOnReturn whether or not to validate objects after they are returned to the {@link #returnObject} method (see {@link #getTestOnReturn})
0358:             */
0359:            public GenericObjectPool(PoolableObjectFactory factory,
0360:                    int maxActive, byte whenExhaustedAction, long maxWait,
0361:                    boolean testOnBorrow, boolean testOnReturn) {
0362:                this (factory, maxActive, whenExhaustedAction, maxWait,
0363:                        DEFAULT_MAX_IDLE, DEFAULT_MIN_IDLE, testOnBorrow,
0364:                        testOnReturn,
0365:                        DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS,
0366:                        DEFAULT_NUM_TESTS_PER_EVICTION_RUN,
0367:                        DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS,
0368:                        DEFAULT_TEST_WHILE_IDLE);
0369:            }
0370:
0371:            /**
0372:             * Create a new <tt>GenericObjectPool</tt> using the specified values.
0373:             * @param factory the (possibly <tt>null</tt>)PoolableObjectFactory to use to create, validate and destroy objects
0374:             * @param maxActive the maximum number of objects that can be borrowed from me at one time (see {@link #setMaxActive})
0375:             * @param whenExhaustedAction the action to take when the pool is exhausted (see {@link #getWhenExhaustedAction})
0376:             * @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})
0377:             * @param maxIdle the maximum number of idle objects in my pool (see {@link #getMaxIdle})
0378:             */
0379:            public GenericObjectPool(PoolableObjectFactory factory,
0380:                    int maxActive, byte whenExhaustedAction, long maxWait,
0381:                    int maxIdle) {
0382:                this (factory, maxActive, whenExhaustedAction, maxWait, maxIdle,
0383:                        DEFAULT_MIN_IDLE, DEFAULT_TEST_ON_BORROW,
0384:                        DEFAULT_TEST_ON_RETURN,
0385:                        DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS,
0386:                        DEFAULT_NUM_TESTS_PER_EVICTION_RUN,
0387:                        DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS,
0388:                        DEFAULT_TEST_WHILE_IDLE);
0389:            }
0390:
0391:            /**
0392:             * Create a new <tt>GenericObjectPool</tt> using the specified values.
0393:             * @param factory the (possibly <tt>null</tt>)PoolableObjectFactory to use to create, validate and destroy objects
0394:             * @param maxActive the maximum number of objects that can be borrowed from me at one time (see {@link #setMaxActive})
0395:             * @param whenExhaustedAction the action to take when the pool is exhausted (see {@link #getWhenExhaustedAction})
0396:             * @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})
0397:             * @param maxIdle the maximum number of idle objects in my pool (see {@link #getMaxIdle})
0398:             * @param testOnBorrow whether or not to validate objects before they are returned by the {@link #borrowObject} method (see {@link #getTestOnBorrow})
0399:             * @param testOnReturn whether or not to validate objects after they are returned to the {@link #returnObject} method (see {@link #getTestOnReturn})
0400:             */
0401:            public GenericObjectPool(PoolableObjectFactory factory,
0402:                    int maxActive, byte whenExhaustedAction, long maxWait,
0403:                    int maxIdle, boolean testOnBorrow, boolean testOnReturn) {
0404:                this (factory, maxActive, whenExhaustedAction, maxWait, maxIdle,
0405:                        DEFAULT_MIN_IDLE, testOnBorrow, testOnReturn,
0406:                        DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS,
0407:                        DEFAULT_NUM_TESTS_PER_EVICTION_RUN,
0408:                        DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS,
0409:                        DEFAULT_TEST_WHILE_IDLE);
0410:            }
0411:
0412:            /**
0413:             * Create a new <tt>GenericObjectPool</tt> using the specified values.
0414:             * @param factory the (possibly <tt>null</tt>)PoolableObjectFactory to use to create, validate and destroy objects
0415:             * @param maxActive the maximum number of objects that can be borrowed from me at one time (see {@link #setMaxActive})
0416:             * @param whenExhaustedAction the action to take when the pool is exhausted (see {@link #setWhenExhaustedAction})
0417:             * @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})
0418:             * @param maxIdle the maximum number of idle objects in my pool (see {@link #setMaxIdle})
0419:             * @param testOnBorrow whether or not to validate objects before they are returned by the {@link #borrowObject} method (see {@link #setTestOnBorrow})
0420:             * @param testOnReturn whether or not to validate objects after they are returned to the {@link #returnObject} method (see {@link #setTestOnReturn})
0421:             * @param timeBetweenEvictionRunsMillis the amount of time (in milliseconds) to sleep between examining idle objects for eviction (see {@link #setTimeBetweenEvictionRunsMillis})
0422:             * @param numTestsPerEvictionRun the number of idle objects to examine per run within the idle object eviction thread (if any) (see {@link #setNumTestsPerEvictionRun})
0423:             * @param minEvictableIdleTimeMillis the minimum number of milliseconds an object can sit idle in the pool before it is eligable for evcition (see {@link #setMinEvictableIdleTimeMillis})
0424:             * @param testWhileIdle whether or not to validate objects in the idle object eviction thread, if any (see {@link #setTestWhileIdle})
0425:             */
0426:            public GenericObjectPool(PoolableObjectFactory factory,
0427:                    int maxActive, byte whenExhaustedAction, long maxWait,
0428:                    int maxIdle, boolean testOnBorrow, boolean testOnReturn,
0429:                    long timeBetweenEvictionRunsMillis,
0430:                    int numTestsPerEvictionRun,
0431:                    long minEvictableIdleTimeMillis, boolean testWhileIdle) {
0432:                this (factory, maxActive, whenExhaustedAction, maxWait, maxIdle,
0433:                        DEFAULT_MIN_IDLE, testOnBorrow, testOnReturn,
0434:                        timeBetweenEvictionRunsMillis, numTestsPerEvictionRun,
0435:                        minEvictableIdleTimeMillis, testWhileIdle);
0436:            }
0437:
0438:            /**
0439:             * Create a new <tt>GenericObjectPool</tt> using the specified values.
0440:             * @param factory the (possibly <tt>null</tt>)PoolableObjectFactory to use to create, validate and destroy objects
0441:             * @param maxActive the maximum number of objects that can be borrowed from me at one time (see {@link #setMaxActive})
0442:             * @param whenExhaustedAction the action to take when the pool is exhausted (see {@link #setWhenExhaustedAction})
0443:             * @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})
0444:             * @param maxIdle the maximum number of idle objects in my pool (see {@link #setMaxIdle})
0445:             * @param minIdle the minimum number of idle objects in my pool (see {@link #setMinIdle})
0446:             * @param testOnBorrow whether or not to validate objects before they are returned by the {@link #borrowObject} method (see {@link #setTestOnBorrow})
0447:             * @param testOnReturn whether or not to validate objects after they are returned to the {@link #returnObject} method (see {@link #setTestOnReturn})
0448:             * @param timeBetweenEvictionRunsMillis the amount of time (in milliseconds) to sleep between examining idle objects for eviction (see {@link #setTimeBetweenEvictionRunsMillis})
0449:             * @param numTestsPerEvictionRun the number of idle objects to examine per run within the idle object eviction thread (if any) (see {@link #setNumTestsPerEvictionRun})
0450:             * @param minEvictableIdleTimeMillis the minimum number of milliseconds an object can sit idle in the pool before it is eligable for evcition (see {@link #setMinEvictableIdleTimeMillis})
0451:             * @param testWhileIdle whether or not to validate objects in the idle object eviction thread, if any (see {@link #setTestWhileIdle})
0452:             */
0453:            public GenericObjectPool(PoolableObjectFactory factory,
0454:                    int maxActive, byte whenExhaustedAction, long maxWait,
0455:                    int maxIdle, int minIdle, boolean testOnBorrow,
0456:                    boolean testOnReturn, long timeBetweenEvictionRunsMillis,
0457:                    int numTestsPerEvictionRun,
0458:                    long minEvictableIdleTimeMillis, boolean testWhileIdle) {
0459:                this (factory, maxActive, whenExhaustedAction, maxWait, maxIdle,
0460:                        minIdle, testOnBorrow, testOnReturn,
0461:                        timeBetweenEvictionRunsMillis, numTestsPerEvictionRun,
0462:                        minEvictableIdleTimeMillis, testWhileIdle,
0463:                        DEFAULT_SOFT_MIN_EVICTABLE_IDLE_TIME_MILLIS);
0464:            }
0465:
0466:            /**
0467:             * Create a new <tt>GenericObjectPool</tt> using the specified values.
0468:             * @param factory the (possibly <tt>null</tt>)PoolableObjectFactory to use to create, validate and destroy objects
0469:             * @param maxActive the maximum number of objects that can be borrowed from me at one time (see {@link #setMaxActive})
0470:             * @param whenExhaustedAction the action to take when the pool is exhausted (see {@link #setWhenExhaustedAction})
0471:             * @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})
0472:             * @param maxIdle the maximum number of idle objects in my pool (see {@link #setMaxIdle})
0473:             * @param minIdle the minimum number of idle objects in my pool (see {@link #setMinIdle})
0474:             * @param testOnBorrow whether or not to validate objects before they are returned by the {@link #borrowObject} method (see {@link #setTestOnBorrow})
0475:             * @param testOnReturn whether or not to validate objects after they are returned to the {@link #returnObject} method (see {@link #setTestOnReturn})
0476:             * @param timeBetweenEvictionRunsMillis the amount of time (in milliseconds) to sleep between examining idle objects for eviction (see {@link #setTimeBetweenEvictionRunsMillis})
0477:             * @param numTestsPerEvictionRun the number of idle objects to examine per run within the idle object eviction thread (if any) (see {@link #setNumTestsPerEvictionRun})
0478:             * @param minEvictableIdleTimeMillis the minimum number of milliseconds an object can sit idle in the pool before it is eligable for evcition (see {@link #setMinEvictableIdleTimeMillis})
0479:             * @param testWhileIdle whether or not to validate objects in the idle object eviction thread, if any (see {@link #setTestWhileIdle})
0480:             * @param softMinEvictableIdleTimeMillis the minimum number of milliseconds an object can sit idle in the pool before it is eligable for evcition with the extra condition that at least "minIdle" amount of object remain in the pool. (see {@link #setSoftMinEvictableIdleTimeMillis})
0481:             */
0482:            public GenericObjectPool(PoolableObjectFactory factory,
0483:                    int maxActive, byte whenExhaustedAction, long maxWait,
0484:                    int maxIdle, int minIdle, boolean testOnBorrow,
0485:                    boolean testOnReturn, long timeBetweenEvictionRunsMillis,
0486:                    int numTestsPerEvictionRun,
0487:                    long minEvictableIdleTimeMillis, boolean testWhileIdle,
0488:                    long softMinEvictableIdleTimeMillis) {
0489:                _factory = factory;
0490:                _maxActive = maxActive;
0491:                switch (whenExhaustedAction) {
0492:                case WHEN_EXHAUSTED_BLOCK:
0493:                case WHEN_EXHAUSTED_FAIL:
0494:                case WHEN_EXHAUSTED_GROW:
0495:                    _whenExhaustedAction = whenExhaustedAction;
0496:                    break;
0497:                default:
0498:                    throw new IllegalArgumentException("whenExhaustedAction "
0499:                            + whenExhaustedAction + " not recognized.");
0500:                }
0501:                _maxWait = maxWait;
0502:                _maxIdle = maxIdle;
0503:                _minIdle = minIdle;
0504:                _testOnBorrow = testOnBorrow;
0505:                _testOnReturn = testOnReturn;
0506:                _timeBetweenEvictionRunsMillis = timeBetweenEvictionRunsMillis;
0507:                _numTestsPerEvictionRun = numTestsPerEvictionRun;
0508:                _minEvictableIdleTimeMillis = minEvictableIdleTimeMillis;
0509:                _softMinEvictableIdleTimeMillis = softMinEvictableIdleTimeMillis;
0510:                _testWhileIdle = testWhileIdle;
0511:
0512:                _pool = new LinkedList();
0513:                startEvictor(_timeBetweenEvictionRunsMillis);
0514:            }
0515:
0516:            //--- public methods ---------------------------------------------
0517:
0518:            //--- configuration methods --------------------------------------
0519:
0520:            /**
0521:             * Returns the cap on the total number of active instances from my pool.
0522:             * @return the cap on the total number of active instances from my pool.
0523:             * @see #setMaxActive
0524:             */
0525:            public synchronized int getMaxActive() {
0526:                return _maxActive;
0527:            }
0528:
0529:            /**
0530:             * Sets the cap on the total number of active instances from my pool.
0531:             * @param maxActive The cap on the total number of active instances from my pool.
0532:             *                  Use a negative value for an infinite number of instances.
0533:             * @see #getMaxActive
0534:             */
0535:            public synchronized void setMaxActive(int maxActive) {
0536:                _maxActive = maxActive;
0537:                notifyAll();
0538:            }
0539:
0540:            /**
0541:             * Returns the action to take when the {@link #borrowObject} method
0542:             * is invoked when the pool is exhausted (the maximum number
0543:             * of "active" objects has been reached).
0544:             *
0545:             * @return one of {@link #WHEN_EXHAUSTED_BLOCK}, {@link #WHEN_EXHAUSTED_FAIL} or {@link #WHEN_EXHAUSTED_GROW}
0546:             * @see #setWhenExhaustedAction
0547:             */
0548:            public synchronized byte getWhenExhaustedAction() {
0549:                return _whenExhaustedAction;
0550:            }
0551:
0552:            /**
0553:             * Sets the action to take when the {@link #borrowObject} method
0554:             * is invoked when the pool is exhausted (the maximum number
0555:             * of "active" objects has been reached).
0556:             *
0557:             * @param whenExhaustedAction the action code, which must be one of
0558:             *        {@link #WHEN_EXHAUSTED_BLOCK}, {@link #WHEN_EXHAUSTED_FAIL},
0559:             *        or {@link #WHEN_EXHAUSTED_GROW}
0560:             * @see #getWhenExhaustedAction
0561:             */
0562:            public synchronized void setWhenExhaustedAction(
0563:                    byte whenExhaustedAction) {
0564:                switch (whenExhaustedAction) {
0565:                case WHEN_EXHAUSTED_BLOCK:
0566:                case WHEN_EXHAUSTED_FAIL:
0567:                case WHEN_EXHAUSTED_GROW:
0568:                    _whenExhaustedAction = whenExhaustedAction;
0569:                    notifyAll();
0570:                    break;
0571:                default:
0572:                    throw new IllegalArgumentException("whenExhaustedAction "
0573:                            + whenExhaustedAction + " not recognized.");
0574:                }
0575:            }
0576:
0577:            /**
0578:             * Returns the maximum amount of time (in milliseconds) the
0579:             * {@link #borrowObject} method should block before throwing
0580:             * an exception when the pool is exhausted and the
0581:             * {@link #setWhenExhaustedAction "when exhausted" action} is
0582:             * {@link #WHEN_EXHAUSTED_BLOCK}.
0583:             *
0584:             * When less than 0, the {@link #borrowObject} method
0585:             * may block indefinitely.
0586:             *
0587:             * @see #setMaxWait
0588:             * @see #setWhenExhaustedAction
0589:             * @see #WHEN_EXHAUSTED_BLOCK
0590:             */
0591:            public synchronized long getMaxWait() {
0592:                return _maxWait;
0593:            }
0594:
0595:            /**
0596:             * Sets the maximum amount of time (in milliseconds) the
0597:             * {@link #borrowObject} method should block before throwing
0598:             * an exception when the pool is exhausted and the
0599:             * {@link #setWhenExhaustedAction "when exhausted" action} is
0600:             * {@link #WHEN_EXHAUSTED_BLOCK}.
0601:             *
0602:             * When less than 0, the {@link #borrowObject} method
0603:             * may block indefinitely.
0604:             *
0605:             * @see #getMaxWait
0606:             * @see #setWhenExhaustedAction
0607:             * @see #WHEN_EXHAUSTED_BLOCK
0608:             */
0609:            public synchronized void setMaxWait(long maxWait) {
0610:                _maxWait = maxWait;
0611:                notifyAll();
0612:            }
0613:
0614:            /**
0615:             * Returns the cap on the number of "idle" instances in the pool.
0616:             * @return the cap on the number of "idle" instances in the pool.
0617:             * @see #setMaxIdle
0618:             */
0619:            public synchronized int getMaxIdle() {
0620:                return _maxIdle;
0621:            }
0622:
0623:            /**
0624:             * Sets the cap on the number of "idle" instances in the pool.
0625:             * @param maxIdle The cap on the number of "idle" instances in the pool.
0626:             *                Use a negative value to indicate an unlimited number
0627:             *                of idle instances.
0628:             * @see #getMaxIdle
0629:             */
0630:            public synchronized void setMaxIdle(int maxIdle) {
0631:                _maxIdle = maxIdle;
0632:                notifyAll();
0633:            }
0634:
0635:            /**
0636:             * Sets the minimum number of objects allowed in the pool
0637:             * before the evictor thread (if active) spawns new objects.
0638:             * (Note no objects are created when: numActive + numIdle >= maxActive)
0639:             *
0640:             * @param minIdle The minimum number of objects.
0641:             * @see #getMinIdle
0642:             */
0643:            public synchronized void setMinIdle(int minIdle) {
0644:                _minIdle = minIdle;
0645:                notifyAll();
0646:            }
0647:
0648:            /**
0649:             * Returns the minimum number of objects allowed in the pool
0650:             * before the evictor thread (if active) spawns new objects.
0651:             * (Note no objects are created when: numActive + numIdle >= maxActive)
0652:             *
0653:             * @return The minimum number of objects.
0654:             * @see #setMinIdle
0655:             */
0656:            public synchronized int getMinIdle() {
0657:                return _minIdle;
0658:            }
0659:
0660:            /**
0661:             * When <tt>true</tt>, objects will be
0662:             * {@link PoolableObjectFactory#validateObject validated}
0663:             * before being returned by the {@link #borrowObject}
0664:             * method.  If the object fails to validate,
0665:             * it will be dropped from the pool, and we will attempt
0666:             * to borrow another.
0667:             *
0668:             * @see #setTestOnBorrow
0669:             */
0670:            public synchronized boolean getTestOnBorrow() {
0671:                return _testOnBorrow;
0672:            }
0673:
0674:            /**
0675:             * When <tt>true</tt>, objects will be
0676:             * {@link PoolableObjectFactory#validateObject validated}
0677:             * before being returned by the {@link #borrowObject}
0678:             * method.  If the object fails to validate,
0679:             * it will be dropped from the pool, and we will attempt
0680:             * to borrow another.
0681:             *
0682:             * @see #getTestOnBorrow
0683:             */
0684:            public synchronized void setTestOnBorrow(boolean testOnBorrow) {
0685:                _testOnBorrow = testOnBorrow;
0686:            }
0687:
0688:            /**
0689:             * When <tt>true</tt>, objects will be
0690:             * {@link PoolableObjectFactory#validateObject validated}
0691:             * before being returned to the pool within the
0692:             * {@link #returnObject}.
0693:             *
0694:             * @see #setTestOnReturn
0695:             */
0696:            public synchronized boolean getTestOnReturn() {
0697:                return _testOnReturn;
0698:            }
0699:
0700:            /**
0701:             * When <tt>true</tt>, objects will be
0702:             * {@link PoolableObjectFactory#validateObject validated}
0703:             * before being returned to the pool within the
0704:             * {@link #returnObject}.
0705:             *
0706:             * @see #getTestOnReturn
0707:             */
0708:            public synchronized void setTestOnReturn(boolean testOnReturn) {
0709:                _testOnReturn = testOnReturn;
0710:            }
0711:
0712:            /**
0713:             * Returns the number of milliseconds to sleep between runs of the
0714:             * idle object evictor thread.
0715:             * When non-positive, no idle object evictor thread will be
0716:             * run.
0717:             *
0718:             * @see #setTimeBetweenEvictionRunsMillis
0719:             */
0720:            public synchronized long getTimeBetweenEvictionRunsMillis() {
0721:                return _timeBetweenEvictionRunsMillis;
0722:            }
0723:
0724:            /**
0725:             * Sets the number of milliseconds to sleep between runs of the
0726:             * idle object evictor thread.
0727:             * When non-positive, no idle object evictor thread will be
0728:             * run.
0729:             *
0730:             * @see #getTimeBetweenEvictionRunsMillis
0731:             */
0732:            public synchronized void setTimeBetweenEvictionRunsMillis(
0733:                    long timeBetweenEvictionRunsMillis) {
0734:                _timeBetweenEvictionRunsMillis = timeBetweenEvictionRunsMillis;
0735:                startEvictor(_timeBetweenEvictionRunsMillis);
0736:            }
0737:
0738:            /**
0739:             * Returns the max number of objects to examine during each run of the
0740:             * idle object evictor thread (if any).
0741:             *
0742:             * @see #setNumTestsPerEvictionRun
0743:             * @see #setTimeBetweenEvictionRunsMillis
0744:             */
0745:            public synchronized int getNumTestsPerEvictionRun() {
0746:                return _numTestsPerEvictionRun;
0747:            }
0748:
0749:            /**
0750:             * Sets the max number of objects to examine during each run of the
0751:             * idle object evictor thread (if any).
0752:             * <p>
0753:             * When a negative value is supplied, <tt>ceil({@link #getNumIdle})/abs({@link #getNumTestsPerEvictionRun})</tt>
0754:             * tests will be run.  I.e., when the value is <i>-n</i>, roughly one <i>n</i>th of the
0755:             * idle objects will be tested per run.
0756:             *
0757:             * @see #getNumTestsPerEvictionRun
0758:             * @see #setTimeBetweenEvictionRunsMillis
0759:             */
0760:            public synchronized void setNumTestsPerEvictionRun(
0761:                    int numTestsPerEvictionRun) {
0762:                _numTestsPerEvictionRun = numTestsPerEvictionRun;
0763:            }
0764:
0765:            /**
0766:             * Returns the minimum amount of time an object may sit idle in the pool
0767:             * before it is eligable for eviction by the idle object evictor
0768:             * (if any).
0769:             *
0770:             * @see #setMinEvictableIdleTimeMillis
0771:             * @see #setTimeBetweenEvictionRunsMillis
0772:             */
0773:            public synchronized long getMinEvictableIdleTimeMillis() {
0774:                return _minEvictableIdleTimeMillis;
0775:            }
0776:
0777:            /**
0778:             * Sets the minimum amount of time an object may sit idle in the pool
0779:             * before it is eligable for eviction by the idle object evictor
0780:             * (if any).
0781:             * When non-positive, no objects will be evicted from the pool
0782:             * due to idle time alone.
0783:             *
0784:             * @see #getMinEvictableIdleTimeMillis
0785:             * @see #setTimeBetweenEvictionRunsMillis
0786:             */
0787:            public synchronized void setMinEvictableIdleTimeMillis(
0788:                    long minEvictableIdleTimeMillis) {
0789:                _minEvictableIdleTimeMillis = minEvictableIdleTimeMillis;
0790:            }
0791:
0792:            /**
0793:             * Returns the minimum amount of time an object may sit idle in the pool
0794:             * before it is eligable for eviction by the idle object evictor
0795:             * (if any), with the extra condition that at least
0796:             * "minIdle" amount of object remain in the pool.
0797:             *
0798:             * @see #setSoftMinEvictableIdleTimeMillis
0799:             */
0800:            public synchronized long getSoftMinEvictableIdleTimeMillis() {
0801:                return _softMinEvictableIdleTimeMillis;
0802:            }
0803:
0804:            /**
0805:             * Sets the minimum amount of time an object may sit idle in the pool
0806:             * before it is eligable for eviction by the idle object evictor
0807:             * (if any), with the extra condition that at least
0808:             * "minIdle" amount of object remain in the pool.
0809:             * When non-positive, no objects will be evicted from the pool
0810:             * due to idle time alone.
0811:             *
0812:             * @see #getSoftMinEvictableIdleTimeMillis
0813:             */
0814:            public synchronized void setSoftMinEvictableIdleTimeMillis(
0815:                    long softMinEvictableIdleTimeMillis) {
0816:                _softMinEvictableIdleTimeMillis = softMinEvictableIdleTimeMillis;
0817:            }
0818:
0819:            /**
0820:             * When <tt>true</tt>, objects will be
0821:             * {@link PoolableObjectFactory#validateObject validated}
0822:             * by the idle object evictor (if any).  If an object
0823:             * fails to validate, it will be dropped from the pool.
0824:             *
0825:             * @see #setTestWhileIdle
0826:             * @see #setTimeBetweenEvictionRunsMillis
0827:             */
0828:            public synchronized boolean getTestWhileIdle() {
0829:                return _testWhileIdle;
0830:            }
0831:
0832:            /**
0833:             * When <tt>true</tt>, objects will be
0834:             * {@link PoolableObjectFactory#validateObject validated}
0835:             * by the idle object evictor (if any).  If an object
0836:             * fails to validate, it will be dropped from the pool.
0837:             *
0838:             * @see #getTestWhileIdle
0839:             * @see #setTimeBetweenEvictionRunsMillis
0840:             */
0841:            public synchronized void setTestWhileIdle(boolean testWhileIdle) {
0842:                _testWhileIdle = testWhileIdle;
0843:            }
0844:
0845:            /**
0846:             * Sets my configuration.
0847:             * @see GenericObjectPool.Config
0848:             */
0849:            public synchronized void setConfig(GenericObjectPool.Config conf) {
0850:                setMaxIdle(conf.maxIdle);
0851:                setMinIdle(conf.minIdle);
0852:                setMaxActive(conf.maxActive);
0853:                setMaxWait(conf.maxWait);
0854:                setWhenExhaustedAction(conf.whenExhaustedAction);
0855:                setTestOnBorrow(conf.testOnBorrow);
0856:                setTestOnReturn(conf.testOnReturn);
0857:                setTestWhileIdle(conf.testWhileIdle);
0858:                setNumTestsPerEvictionRun(conf.numTestsPerEvictionRun);
0859:                setMinEvictableIdleTimeMillis(conf.minEvictableIdleTimeMillis);
0860:                setTimeBetweenEvictionRunsMillis(conf.timeBetweenEvictionRunsMillis);
0861:                notifyAll();
0862:            }
0863:
0864:            //-- ObjectPool methods ------------------------------------------
0865:
0866:            public synchronized Object borrowObject() throws Exception {
0867:                assertOpen();
0868:                long starttime = System.currentTimeMillis();
0869:                for (;;) {
0870:                    ObjectTimestampPair pair = null;
0871:
0872:                    // if there are any sleeping, just grab one of those
0873:                    try {
0874:                        pair = (ObjectTimestampPair) (_pool.removeFirst());
0875:                    } catch (NoSuchElementException e) {
0876:                        ; /* ignored */
0877:                    }
0878:
0879:                    // otherwise
0880:                    if (null == pair) {
0881:                        // check if we can create one
0882:                        // (note we know that the num sleeping is 0, else we wouldn't be here)
0883:                        if (_maxActive < 0 || _numActive < _maxActive) {
0884:                            // allow new object to be created
0885:                        } else {
0886:                            // the pool is exhausted
0887:                            switch (_whenExhaustedAction) {
0888:                            case WHEN_EXHAUSTED_GROW:
0889:                                // allow new object to be created
0890:                                break;
0891:                            case WHEN_EXHAUSTED_FAIL:
0892:                                throw new NoSuchElementException(
0893:                                        "Pool exhausted");
0894:                            case WHEN_EXHAUSTED_BLOCK:
0895:                                try {
0896:                                    if (_maxWait <= 0) {
0897:                                        wait();
0898:                                    } else {
0899:                                        // this code may be executed again after a notify then continue cycle
0900:                                        // so, need to calculate the amount of time to wait
0901:                                        final long elapsed = (System
0902:                                                .currentTimeMillis() - starttime);
0903:                                        final long waitTime = _maxWait
0904:                                                - elapsed;
0905:                                        if (waitTime > 0) {
0906:                                            wait(waitTime);
0907:                                        }
0908:                                    }
0909:                                } catch (InterruptedException e) {
0910:                                    // ignored
0911:                                }
0912:                                if (_maxWait > 0
0913:                                        && ((System.currentTimeMillis() - starttime) >= _maxWait)) {
0914:                                    throw new NoSuchElementException(
0915:                                            "Timeout waiting for idle object");
0916:                                } else {
0917:                                    continue; // keep looping
0918:                                }
0919:                            default:
0920:                                throw new IllegalArgumentException(
0921:                                        "WhenExhaustedAction property "
0922:                                                + _whenExhaustedAction
0923:                                                + " not recognized.");
0924:                            }
0925:                        }
0926:                    }
0927:                    _numActive++;
0928:
0929:                    // create new object when needed
0930:                    boolean newlyCreated = false;
0931:                    if (null == pair) {
0932:                        try {
0933:                            Object obj = _factory.makeObject();
0934:                            pair = new ObjectTimestampPair(obj);
0935:                            newlyCreated = true;
0936:                        } finally {
0937:                            if (!newlyCreated) {
0938:                                // object cannot be created
0939:                                _numActive--;
0940:                                notifyAll();
0941:                            }
0942:                        }
0943:                    }
0944:
0945:                    // activate & validate the object
0946:                    try {
0947:                        _factory.activateObject(pair.value);
0948:                        if (_testOnBorrow
0949:                                && !_factory.validateObject(pair.value)) {
0950:                            throw new Exception("ValidateObject failed");
0951:                        }
0952:                        return pair.value;
0953:                    } catch (Throwable e) {
0954:                        // object cannot be activated or is invalid
0955:                        _numActive--;
0956:                        notifyAll();
0957:                        try {
0958:                            _factory.destroyObject(pair.value);
0959:                        } catch (Throwable e2) {
0960:                            // cannot destroy broken object
0961:                        }
0962:                        if (newlyCreated) {
0963:                            throw new NoSuchElementException(
0964:                                    "Could not create a validated object, cause: "
0965:                                            + e.getMessage());
0966:                        } else {
0967:                            continue; // keep looping
0968:                        }
0969:                    }
0970:                }
0971:            }
0972:
0973:            public synchronized void invalidateObject(Object obj)
0974:                    throws Exception {
0975:                assertOpen();
0976:                try {
0977:                    _factory.destroyObject(obj);
0978:                } finally {
0979:                    _numActive--;
0980:                    notifyAll(); // _numActive has changed
0981:                }
0982:            }
0983:
0984:            public synchronized void clear() {
0985:                assertOpen();
0986:                for (Iterator it = _pool.iterator(); it.hasNext();) {
0987:                    try {
0988:                        _factory.destroyObject(((ObjectTimestampPair) (it
0989:                                .next())).value);
0990:                    } catch (Exception e) {
0991:                        // ignore error, keep destroying the rest
0992:                    }
0993:                    it.remove();
0994:                }
0995:                _pool.clear();
0996:                notifyAll(); // num sleeping has changed
0997:            }
0998:
0999:            public synchronized int getNumActive() {
1000:                assertOpen();
1001:                return _numActive;
1002:            }
1003:
1004:            public synchronized int getNumIdle() {
1005:                assertOpen();
1006:                return _pool.size();
1007:            }
1008:
1009:            public synchronized void returnObject(Object obj) throws Exception {
1010:                assertOpen();
1011:                addObjectToPool(obj, true);
1012:            }
1013:
1014:            private void addObjectToPool(Object obj, boolean decrementNumActive)
1015:                    throws Exception {
1016:                boolean success = true;
1017:                if (_testOnReturn && !(_factory.validateObject(obj))) {
1018:                    success = false;
1019:                } else {
1020:                    try {
1021:                        _factory.passivateObject(obj);
1022:                    } catch (Exception e) {
1023:                        success = false;
1024:                    }
1025:                }
1026:
1027:                boolean shouldDestroy = !success;
1028:
1029:                if (decrementNumActive) {
1030:                    _numActive--;
1031:                }
1032:                if ((_maxIdle >= 0) && (_pool.size() >= _maxIdle)) {
1033:                    shouldDestroy = true;
1034:                } else if (success) {
1035:                    _pool.addLast(new ObjectTimestampPair(obj));
1036:                }
1037:                notifyAll(); // _numActive has changed
1038:
1039:                if (shouldDestroy) {
1040:                    try {
1041:                        _factory.destroyObject(obj);
1042:                    } catch (Exception e) {
1043:                        // ignored
1044:                    }
1045:                }
1046:            }
1047:
1048:            public synchronized void close() throws Exception {
1049:                clear();
1050:                _pool = null;
1051:                _factory = null;
1052:                startEvictor(-1L);
1053:                super .close();
1054:            }
1055:
1056:            public synchronized void setFactory(PoolableObjectFactory factory)
1057:                    throws IllegalStateException {
1058:                assertOpen();
1059:                if (0 < getNumActive()) {
1060:                    throw new IllegalStateException(
1061:                            "Objects are already active");
1062:                } else {
1063:                    clear();
1064:                    _factory = factory;
1065:                }
1066:            }
1067:
1068:            public synchronized void evict() throws Exception {
1069:                assertOpen();
1070:                if (!_pool.isEmpty()) {
1071:                    ListIterator iter;
1072:                    if (evictLastIndex < 0) {
1073:                        iter = _pool.listIterator(_pool.size());
1074:                    } else {
1075:                        iter = _pool.listIterator(evictLastIndex);
1076:                    }
1077:                    for (int i = 0, m = getNumTests(); i < m; i++) {
1078:                        if (!iter.hasPrevious()) {
1079:                            iter = _pool.listIterator(_pool.size());
1080:                        }
1081:                        boolean removeObject = false;
1082:                        final ObjectTimestampPair pair = (ObjectTimestampPair) (iter
1083:                                .previous());
1084:                        final long idleTimeMilis = System.currentTimeMillis()
1085:                                - pair.tstamp;
1086:                        if ((_minEvictableIdleTimeMillis > 0)
1087:                                && (idleTimeMilis > _minEvictableIdleTimeMillis)) {
1088:                            removeObject = true;
1089:                        } else if ((_softMinEvictableIdleTimeMillis > 0)
1090:                                && (idleTimeMilis > _softMinEvictableIdleTimeMillis)
1091:                                && (getNumIdle() > getMinIdle())) {
1092:                            removeObject = true;
1093:                        }
1094:                        if (_testWhileIdle && !removeObject) {
1095:                            boolean active = false;
1096:                            try {
1097:                                _factory.activateObject(pair.value);
1098:                                active = true;
1099:                            } catch (Exception e) {
1100:                                removeObject = true;
1101:                            }
1102:                            if (active) {
1103:                                if (!_factory.validateObject(pair.value)) {
1104:                                    removeObject = true;
1105:                                } else {
1106:                                    try {
1107:                                        _factory.passivateObject(pair.value);
1108:                                    } catch (Exception e) {
1109:                                        removeObject = true;
1110:                                    }
1111:                                }
1112:                            }
1113:                        }
1114:                        if (removeObject) {
1115:                            try {
1116:                                iter.remove();
1117:                                _factory.destroyObject(pair.value);
1118:                            } catch (Exception e) {
1119:                                // ignored
1120:                            }
1121:                        }
1122:                    }
1123:                    evictLastIndex = iter.previousIndex(); // resume from here
1124:                } // if !empty
1125:            }
1126:
1127:            /**
1128:             * Check to see if we are below our minimum number of objects
1129:             * if so enough to bring us back to our minimum.
1130:             */
1131:            private void ensureMinIdle() throws Exception {
1132:                // this method isn't synchronized so the
1133:                // calculateDeficit is done at the beginning
1134:                // as a loop limit and a second time inside the loop
1135:                // to stop when another thread already returned the
1136:                // needed objects
1137:                int objectDeficit = calculateDeficit();
1138:                for (int j = 0; j < objectDeficit && calculateDeficit() > 0; j++) {
1139:                    addObject();
1140:                }
1141:            }
1142:
1143:            private synchronized int calculateDeficit() {
1144:                int objectDeficit = getMinIdle() - getNumIdle();
1145:                if (_maxActive > 0) {
1146:                    int growLimit = Math.max(0, getMaxActive() - getNumActive()
1147:                            - getNumIdle());
1148:                    objectDeficit = Math.min(objectDeficit, growLimit);
1149:                }
1150:                return objectDeficit;
1151:            }
1152:
1153:            /**
1154:             * Create an object, and place it into the pool.
1155:             * addObject() is useful for "pre-loading" a pool with idle objects.
1156:             */
1157:            public synchronized void addObject() throws Exception {
1158:                assertOpen();
1159:                Object obj = _factory.makeObject();
1160:                addObjectToPool(obj, false);
1161:            }
1162:
1163:            //--- non-public methods ----------------------------------------
1164:
1165:            /**
1166:             * Start the eviction thread or service, or when
1167:             * <i>delay</i> is non-positive, stop it
1168:             * if it is already running.
1169:             */
1170:            protected synchronized void startEvictor(long delay) {
1171:                if (null != _evictor) {
1172:                    _evictor.cancel();
1173:                    _evictor = null;
1174:                }
1175:                if (delay > 0) {
1176:                    _evictor = new Evictor();
1177:                    EVICTION_TIMER.schedule(_evictor, delay, delay);
1178:                }
1179:            }
1180:
1181:            synchronized String debugInfo() {
1182:                StringBuffer buf = new StringBuffer();
1183:                buf.append("Active: ").append(getNumActive()).append("\n");
1184:                buf.append("Idle: ").append(getNumIdle()).append("\n");
1185:                buf.append("Idle Objects:\n");
1186:                Iterator it = _pool.iterator();
1187:                long time = System.currentTimeMillis();
1188:                while (it.hasNext()) {
1189:                    ObjectTimestampPair pair = (ObjectTimestampPair) (it.next());
1190:                    buf.append("\t").append(pair.value).append("\t").append(
1191:                            time - pair.tstamp).append("\n");
1192:                }
1193:                return buf.toString();
1194:            }
1195:
1196:            private int getNumTests() {
1197:                if (_numTestsPerEvictionRun >= 0) {
1198:                    return Math.min(_numTestsPerEvictionRun, _pool.size());
1199:                } else {
1200:                    return (int) (Math.ceil((double) _pool.size()
1201:                            / Math.abs((double) _numTestsPerEvictionRun)));
1202:                }
1203:            }
1204:
1205:            //--- inner classes ----------------------------------------------
1206:
1207:            /**
1208:             * The idle object evictor {@link TimerTask}.
1209:             * @see GenericObjectPool#setTimeBetweenEvictionRunsMillis
1210:             */
1211:            private class Evictor extends TimerTask {
1212:                public void run() {
1213:                    try {
1214:                        evict();
1215:                    } catch (Exception e) {
1216:                        // ignored
1217:                    }
1218:                    try {
1219:                        ensureMinIdle();
1220:                    } catch (Exception e) {
1221:                        // ignored
1222:                    }
1223:                }
1224:            }
1225:
1226:            /**
1227:             * A simple "struct" encapsulating the
1228:             * configuration information for a {@link GenericObjectPool}.
1229:             * @see GenericObjectPool#GenericObjectPool(org.apache.commons.pool.PoolableObjectFactory,org.apache.commons.pool.impl.GenericObjectPool.Config)
1230:             * @see GenericObjectPool#setConfig
1231:             */
1232:            public static class Config {
1233:                public int maxIdle = GenericObjectPool.DEFAULT_MAX_IDLE;
1234:                public int minIdle = GenericObjectPool.DEFAULT_MIN_IDLE;
1235:                public int maxActive = GenericObjectPool.DEFAULT_MAX_ACTIVE;
1236:                public long maxWait = GenericObjectPool.DEFAULT_MAX_WAIT;
1237:                public byte whenExhaustedAction = GenericObjectPool.DEFAULT_WHEN_EXHAUSTED_ACTION;
1238:                public boolean testOnBorrow = GenericObjectPool.DEFAULT_TEST_ON_BORROW;
1239:                public boolean testOnReturn = GenericObjectPool.DEFAULT_TEST_ON_RETURN;
1240:                public boolean testWhileIdle = GenericObjectPool.DEFAULT_TEST_WHILE_IDLE;
1241:                public long timeBetweenEvictionRunsMillis = GenericObjectPool.DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS;
1242:                public int numTestsPerEvictionRun = GenericObjectPool.DEFAULT_NUM_TESTS_PER_EVICTION_RUN;
1243:                public long minEvictableIdleTimeMillis = GenericObjectPool.DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS;
1244:                public long softMinEvictableIdleTimeMillis = GenericObjectPool.DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS;
1245:            }
1246:
1247:            //--- private attributes ---------------------------------------
1248:
1249:            /**
1250:             * The cap on the number of idle instances in the pool.
1251:             * @see #setMaxIdle
1252:             * @see #getMaxIdle
1253:             */
1254:            private int _maxIdle = DEFAULT_MAX_IDLE;
1255:
1256:            /**
1257:             * The cap on the minimum number of idle instances in the pool.
1258:             * @see #setMinIdle
1259:             * @see #getMinIdle
1260:             */
1261:            private int _minIdle = DEFAULT_MIN_IDLE;
1262:
1263:            /**
1264:             * The cap on the total number of active instances from the pool.
1265:             * @see #setMaxActive
1266:             * @see #getMaxActive
1267:             */
1268:            private int _maxActive = DEFAULT_MAX_ACTIVE;
1269:
1270:            /**
1271:             * The maximum amount of time (in millis) the
1272:             * {@link #borrowObject} method should block before throwing
1273:             * an exception when the pool is exhausted and the
1274:             * {@link #getWhenExhaustedAction "when exhausted" action} is
1275:             * {@link #WHEN_EXHAUSTED_BLOCK}.
1276:             *
1277:             * When less than 0, the {@link #borrowObject} method
1278:             * may block indefinitely.
1279:             *
1280:             * @see #setMaxWait
1281:             * @see #getMaxWait
1282:             * @see #WHEN_EXHAUSTED_BLOCK
1283:             * @see #setWhenExhaustedAction
1284:             * @see #getWhenExhaustedAction
1285:             */
1286:            private long _maxWait = DEFAULT_MAX_WAIT;
1287:
1288:            /**
1289:             * The action to take when the {@link #borrowObject} method
1290:             * is invoked when the pool is exhausted (the maximum number
1291:             * of "active" objects has been reached).
1292:             *
1293:             * @see #WHEN_EXHAUSTED_BLOCK
1294:             * @see #WHEN_EXHAUSTED_FAIL
1295:             * @see #WHEN_EXHAUSTED_GROW
1296:             * @see #DEFAULT_WHEN_EXHAUSTED_ACTION
1297:             * @see #setWhenExhaustedAction
1298:             * @see #getWhenExhaustedAction
1299:             */
1300:            private byte _whenExhaustedAction = DEFAULT_WHEN_EXHAUSTED_ACTION;
1301:
1302:            /**
1303:             * When <tt>true</tt>, objects will be
1304:             * {@link PoolableObjectFactory#validateObject validated}
1305:             * before being returned by the {@link #borrowObject}
1306:             * method.  If the object fails to validate,
1307:             * it will be dropped from the pool, and we will attempt
1308:             * to borrow another.
1309:             *
1310:             * @see #setTestOnBorrow
1311:             * @see #getTestOnBorrow
1312:             */
1313:            private boolean _testOnBorrow = DEFAULT_TEST_ON_BORROW;
1314:
1315:            /**
1316:             * When <tt>true</tt>, objects will be
1317:             * {@link PoolableObjectFactory#validateObject validated}
1318:             * before being returned to the pool within the
1319:             * {@link #returnObject}.
1320:             *
1321:             * @see #getTestOnReturn
1322:             * @see #setTestOnReturn
1323:             */
1324:            private boolean _testOnReturn = DEFAULT_TEST_ON_RETURN;
1325:
1326:            /**
1327:             * When <tt>true</tt>, objects will be
1328:             * {@link PoolableObjectFactory#validateObject validated}
1329:             * by the idle object evictor (if any).  If an object
1330:             * fails to validate, it will be dropped from the pool.
1331:             *
1332:             * @see #setTestWhileIdle
1333:             * @see #getTestWhileIdle
1334:             * @see #getTimeBetweenEvictionRunsMillis
1335:             * @see #setTimeBetweenEvictionRunsMillis
1336:             */
1337:            private boolean _testWhileIdle = DEFAULT_TEST_WHILE_IDLE;
1338:
1339:            /**
1340:             * The number of milliseconds to sleep between runs of the
1341:             * idle object evictor thread.
1342:             * When non-positive, no idle object evictor thread will be
1343:             * run.
1344:             *
1345:             * @see #setTimeBetweenEvictionRunsMillis
1346:             * @see #getTimeBetweenEvictionRunsMillis
1347:             */
1348:            private long _timeBetweenEvictionRunsMillis = DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS;
1349:
1350:            /**
1351:             * The max number of objects to examine during each run of the
1352:             * idle object evictor thread (if any).
1353:             * <p>
1354:             * When a negative value is supplied, <tt>ceil({@link #getNumIdle})/abs({@link #getNumTestsPerEvictionRun})</tt>
1355:             * tests will be run.  I.e., when the value is <i>-n</i>, roughly one <i>n</i>th of the
1356:             * idle objects will be tested per run.
1357:             *
1358:             * @see #setNumTestsPerEvictionRun
1359:             * @see #getNumTestsPerEvictionRun
1360:             * @see #getTimeBetweenEvictionRunsMillis
1361:             * @see #setTimeBetweenEvictionRunsMillis
1362:             */
1363:            private int _numTestsPerEvictionRun = DEFAULT_NUM_TESTS_PER_EVICTION_RUN;
1364:
1365:            /**
1366:             * The minimum amount of time an object may sit idle in the pool
1367:             * before it is eligable for eviction by the idle object evictor
1368:             * (if any).
1369:             * When non-positive, no objects will be evicted from the pool
1370:             * due to idle time alone.
1371:             *
1372:             * @see #setMinEvictableIdleTimeMillis
1373:             * @see #getMinEvictableIdleTimeMillis
1374:             * @see #getTimeBetweenEvictionRunsMillis
1375:             * @see #setTimeBetweenEvictionRunsMillis
1376:             */
1377:            private long _minEvictableIdleTimeMillis = DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS;
1378:
1379:            /**
1380:             * The minimum amount of time an object may sit idle in the pool
1381:             * before it is eligable for eviction by the idle object evictor
1382:             * (if any), with the extra condition that at least
1383:             * "minIdle" amount of object remain in the pool.
1384:             * When non-positive, no objects will be evicted from the pool
1385:             * due to idle time alone.
1386:             *
1387:             * @see #setSoftMinEvictableIdleTimeMillis
1388:             * @see #getSoftMinEvictableIdleTimeMillis
1389:             */
1390:            private long _softMinEvictableIdleTimeMillis = DEFAULT_SOFT_MIN_EVICTABLE_IDLE_TIME_MILLIS;
1391:
1392:            /** My pool. */
1393:            private LinkedList _pool = null;
1394:
1395:            /** My {@link PoolableObjectFactory}. */
1396:            private PoolableObjectFactory _factory = null;
1397:
1398:            /**
1399:             * The number of objects {@link #borrowObject} borrowed
1400:             * from the pool, but not yet returned.
1401:             */
1402:            private int _numActive = 0;
1403:
1404:            /**
1405:             * My idle object eviction {@link TimerTask}, if any.
1406:             */
1407:            private Evictor _evictor = null;
1408:
1409:            /**
1410:             * Position in the _pool where the _evictor last stopped.
1411:             */
1412:            private int evictLastIndex = -1;
1413:        }
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.