1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17 package org.apache.commons.pool.impl;
18
19 import java.util.Iterator;
20 import java.util.NoSuchElementException;
21 import java.util.LinkedList;
22 import java.util.ListIterator;
23 import java.util.Timer;
24 import java.util.TimerTask;
25
26 import org.apache.commons.pool.BaseObjectPool;
27 import org.apache.commons.pool.ObjectPool;
28 import org.apache.commons.pool.PoolableObjectFactory;
29 import org.apache.commons.pool.impl.GenericKeyedObjectPool.ObjectTimestampPair;
30
31 /***
32 * A configurable {@link ObjectPool} implementation.
33 * <p>
34 * When coupled with the appropriate {@link PoolableObjectFactory},
35 * <tt>GenericObjectPool</tt> provides robust pooling functionality for
36 * arbitrary objects.
37 * <p>
38 * A <tt>GenericObjectPool</tt> provides a number of configurable parameters:
39 * <ul>
40 * <li>
41 * {@link #setMaxActive <i>maxActive</i>} controls the maximum number of objects that can
42 * be borrowed from the pool at one time. When non-positive, there
43 * is no limit to the number of objects that may be active at one time.
44 * When {@link #setMaxActive <i>maxActive</i>} is exceeded, the pool is said to be exhausted.
45 * </li>
46 * <li>
47 * {@link #setMaxIdle <i>maxIdle</i>} controls the maximum number of objects that can
48 * sit idle in the pool at any time. When negative, there
49 * is no limit to the number of objects that may be idle at one time.
50 * </li>
51 * <li>
52 * {@link #setWhenExhaustedAction <i>whenExhaustedAction</i>} specifies the
53 * behaviour of the {@link #borrowObject} method when the pool is exhausted:
54 * <ul>
55 * <li>
56 * When {@link #setWhenExhaustedAction <i>whenExhaustedAction</i>} is
57 * {@link #WHEN_EXHAUSTED_FAIL}, {@link #borrowObject} will throw
58 * a {@link NoSuchElementException}
59 * </li>
60 * <li>
61 * When {@link #setWhenExhaustedAction <i>whenExhaustedAction</i>} is
62 * {@link #WHEN_EXHAUSTED_GROW}, {@link #borrowObject} will create a new
63 * object and return it(essentially making {@link #setMaxActive <i>maxActive</i>}
64 * meaningless.)
65 * </li>
66 * <li>
67 * When {@link #setWhenExhaustedAction <i>whenExhaustedAction</i>}
68 * is {@link #WHEN_EXHAUSTED_BLOCK}, {@link #borrowObject} will block
69 * (invoke {@link Object#wait} until a new or idle object is available.
70 * If a positive {@link #setMaxWait <i>maxWait</i>}
71 * value is supplied, the {@link #borrowObject} will block for at
72 * most that many milliseconds, after which a {@link NoSuchElementException}
73 * will be thrown. If {@link #setMaxWait <i>maxWait</i>} is non-positive,
74 * the {@link #borrowObject} method will block indefinitely.
75 * </li>
76 * </ul>
77 * </li>
78 * <li>
79 * When {@link #setTestOnBorrow <i>testOnBorrow</i>} is set, the pool will
80 * attempt to validate each object before it is returned from the
81 * {@link #borrowObject} method. (Using the provided factory's
82 * {@link PoolableObjectFactory#validateObject} method.) Objects that fail
83 * to validate will be dropped from the pool, and a different object will
84 * be borrowed.
85 * </li>
86 * <li>
87 * When {@link #setTestOnReturn <i>testOnReturn</i>} is set, the pool will
88 * attempt to validate each object before it is returned to the pool in the
89 * {@link #returnObject} method. (Using the provided factory's
90 * {@link PoolableObjectFactory#validateObject}
91 * method.) Objects that fail to validate will be dropped from the pool.
92 * </li>
93 * </ul>
94 * <p>
95 * Optionally, one may configure the pool to examine and possibly evict objects as they
96 * sit idle in the pool. This is performed by an "idle object eviction" thread, which
97 * runs asychronously. The idle object eviction thread may be configured using the
98 * following attributes:
99 * <ul>
100 * <li>
101 * {@link #setTimeBetweenEvictionRunsMillis <i>timeBetweenEvictionRunsMillis</i>}
102 * indicates how long the eviction thread should sleep before "runs" of examining
103 * idle objects. When non-positive, no eviction thread will be launched.
104 * </li>
105 * <li>
106 * {@link #setMinEvictableIdleTimeMillis <i>minEvictableIdleTimeMillis</i>}
107 * specifies the minimum amount of time that an object may sit idle in the pool
108 * before it is eligable for eviction due to idle time. When non-positive, no object
109 * will be dropped from the pool due to idle time alone.
110 * </li>
111 * <li>
112 * {@link #setTestWhileIdle <i>testWhileIdle</i>} indicates whether or not idle
113 * objects should be validated using the factory's
114 * {@link PoolableObjectFactory#validateObject} method. Objects
115 * that fail to validate will be dropped from the pool.
116 * </li>
117 * </ul>
118 * <p>
119 * GenericObjectPool is not usable without a {@link PoolableObjectFactory}. A
120 * non-<code>null</code> factory must be provided either as a constructor argument
121 * or via a call to {@link #setFactory} before the pool is used.
122 *
123 * @see GenericKeyedObjectPool
124 * @author Rodney Waldhoff
125 * @author Dirk Verbeeck
126 * @version $Revision: 4672 $ $Date: 2006-09-27 00:03:16 +0000 (Wed, 27 Sep 2006) $
127 */
128 @SuppressWarnings("unchecked")
129 public class GenericObjectPool extends BaseObjectPool implements ObjectPool {
130
131
132
133 /***
134 * A "when exhausted action" type indicating that when the pool is
135 * exhausted (i.e., the maximum number of active objects has
136 * been reached), the {@link #borrowObject}
137 * method should fail, throwing a {@link NoSuchElementException}.
138 * @see #WHEN_EXHAUSTED_BLOCK
139 * @see #WHEN_EXHAUSTED_GROW
140 * @see #setWhenExhaustedAction
141 */
142 public static final byte WHEN_EXHAUSTED_FAIL = 0;
143
144 /***
145 * A "when exhausted action" type indicating that when the pool
146 * is exhausted (i.e., the maximum number
147 * of active objects has been reached), the {@link #borrowObject}
148 * method should block until a new object is available, or the
149 * {@link #getMaxWait maximum wait time} has been reached.
150 * @see #WHEN_EXHAUSTED_FAIL
151 * @see #WHEN_EXHAUSTED_GROW
152 * @see #setMaxWait
153 * @see #getMaxWait
154 * @see #setWhenExhaustedAction
155 */
156 public static final byte WHEN_EXHAUSTED_BLOCK = 1;
157
158 /***
159 * A "when exhausted action" type indicating that when the pool is
160 * exhausted (i.e., the maximum number
161 * of active objects has been reached), the {@link #borrowObject}
162 * method should simply create a new object anyway.
163 * @see #WHEN_EXHAUSTED_FAIL
164 * @see #WHEN_EXHAUSTED_GROW
165 * @see #setWhenExhaustedAction
166 */
167 public static final byte WHEN_EXHAUSTED_GROW = 2;
168
169 /***
170 * The default cap on the number of "sleeping" instances in the pool.
171 * @see #getMaxIdle
172 * @see #setMaxIdle
173 */
174 public static final int DEFAULT_MAX_IDLE = 8;
175
176 /***
177 * The default minimum number of "sleeping" instances in the pool
178 * before before the evictor thread (if active) spawns new objects.
179 * @see #getMinIdle
180 * @see #setMinIdle
181 */
182 public static final int DEFAULT_MIN_IDLE = 0;
183
184 /***
185 * The default cap on the total number of active instances from the pool.
186 * @see #getMaxActive
187 */
188 public static final int DEFAULT_MAX_ACTIVE = 8;
189
190 /***
191 * The default "when exhausted action" for the pool.
192 * @see #WHEN_EXHAUSTED_BLOCK
193 * @see #WHEN_EXHAUSTED_FAIL
194 * @see #WHEN_EXHAUSTED_GROW
195 * @see #setWhenExhaustedAction
196 */
197 public static final byte DEFAULT_WHEN_EXHAUSTED_ACTION = WHEN_EXHAUSTED_BLOCK;
198
199 /***
200 * The default maximum amount of time (in millis) the
201 * {@link #borrowObject} method should block before throwing
202 * an exception when the pool is exhausted and the
203 * {@link #getWhenExhaustedAction "when exhausted" action} is
204 * {@link #WHEN_EXHAUSTED_BLOCK}.
205 * @see #getMaxWait
206 * @see #setMaxWait
207 */
208 public static final long DEFAULT_MAX_WAIT = -1L;
209
210 /***
211 * The default "test on borrow" value.
212 * @see #getTestOnBorrow
213 * @see #setTestOnBorrow
214 */
215 public static final boolean DEFAULT_TEST_ON_BORROW = false;
216
217 /***
218 * The default "test on return" value.
219 * @see #getTestOnReturn
220 * @see #setTestOnReturn
221 */
222 public static final boolean DEFAULT_TEST_ON_RETURN = false;
223
224 /***
225 * The default "test while idle" value.
226 * @see #getTestWhileIdle
227 * @see #setTestWhileIdle
228 * @see #getTimeBetweenEvictionRunsMillis
229 * @see #setTimeBetweenEvictionRunsMillis
230 */
231 public static final boolean DEFAULT_TEST_WHILE_IDLE = false;
232
233 /***
234 * The default "time between eviction runs" value.
235 * @see #getTimeBetweenEvictionRunsMillis
236 * @see #setTimeBetweenEvictionRunsMillis
237 */
238 public static final long DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS = -1L;
239
240 /***
241 * The default number of objects to examine per run in the
242 * idle object evictor.
243 * @see #getNumTestsPerEvictionRun
244 * @see #setNumTestsPerEvictionRun
245 * @see #getTimeBetweenEvictionRunsMillis
246 * @see #setTimeBetweenEvictionRunsMillis
247 */
248 public static final int DEFAULT_NUM_TESTS_PER_EVICTION_RUN = 3;
249
250 /***
251 * The default value for {@link #getMinEvictableIdleTimeMillis}.
252 * @see #getMinEvictableIdleTimeMillis
253 * @see #setMinEvictableIdleTimeMillis
254 */
255 public static final long DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS = 1000L * 60L * 30L;
256
257 /***
258 * The default value for {@link #getSoftMinEvictableIdleTimeMillis}.
259 * @see #getSoftMinEvictableIdleTimeMillis
260 * @see #setSoftMinEvictableIdleTimeMillis
261 */
262 public static final long DEFAULT_SOFT_MIN_EVICTABLE_IDLE_TIME_MILLIS = -1;
263
264
265
266 /***
267 * Idle object evition Timer. Shared between all {@link GenericObjectPool}s and {@link GenericKeyedObjectPool} s.
268 */
269 static final Timer EVICTION_TIMER = new Timer(true);
270
271
272
273 /***
274 * Create a new <tt>GenericObjectPool</tt>.
275 */
276 public GenericObjectPool() {
277 this(null,DEFAULT_MAX_ACTIVE,DEFAULT_WHEN_EXHAUSTED_ACTION,DEFAULT_MAX_WAIT,DEFAULT_MAX_IDLE,DEFAULT_MIN_IDLE,DEFAULT_TEST_ON_BORROW,DEFAULT_TEST_ON_RETURN,DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS,DEFAULT_NUM_TESTS_PER_EVICTION_RUN,DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS,DEFAULT_TEST_WHILE_IDLE);
278 }
279
280 /***
281 * Create a new <tt>GenericObjectPool</tt> using the specified values.
282 * @param factory the (possibly <tt>null</tt>)PoolableObjectFactory to use to create, validate and destroy objects
283 */
284 public GenericObjectPool(PoolableObjectFactory factory) {
285 this(factory,DEFAULT_MAX_ACTIVE,DEFAULT_WHEN_EXHAUSTED_ACTION,DEFAULT_MAX_WAIT,DEFAULT_MAX_IDLE,DEFAULT_MIN_IDLE,DEFAULT_TEST_ON_BORROW,DEFAULT_TEST_ON_RETURN,DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS,DEFAULT_NUM_TESTS_PER_EVICTION_RUN,DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS,DEFAULT_TEST_WHILE_IDLE);
286 }
287
288 /***
289 * Create a new <tt>GenericObjectPool</tt> using the specified values.
290 * @param factory the (possibly <tt>null</tt>)PoolableObjectFactory to use to create, validate and destroy objects
291 * @param config a non-<tt>null</tt> {@link GenericObjectPool.Config} describing my configuration
292 */
293 public GenericObjectPool(PoolableObjectFactory factory, GenericObjectPool.Config config) {
294 this(factory,config.maxActive,config.whenExhaustedAction,config.maxWait,config.maxIdle,config.minIdle,config.testOnBorrow,config.testOnReturn,config.timeBetweenEvictionRunsMillis,config.numTestsPerEvictionRun,config.minEvictableIdleTimeMillis,config.testWhileIdle);
295 }
296
297 /***
298 * Create a new <tt>GenericObjectPool</tt> using the specified values.
299 * @param factory the (possibly <tt>null</tt>)PoolableObjectFactory to use to create, validate and destroy objects
300 * @param maxActive the maximum number of objects that can be borrowed from me at one time (see {@link #setMaxActive})
301 */
302 public GenericObjectPool(PoolableObjectFactory factory, int maxActive) {
303 this(factory,maxActive,DEFAULT_WHEN_EXHAUSTED_ACTION,DEFAULT_MAX_WAIT,DEFAULT_MAX_IDLE,DEFAULT_MIN_IDLE,DEFAULT_TEST_ON_BORROW,DEFAULT_TEST_ON_RETURN,DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS,DEFAULT_NUM_TESTS_PER_EVICTION_RUN,DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS,DEFAULT_TEST_WHILE_IDLE);
304 }
305
306 /***
307 * Create a new <tt>GenericObjectPool</tt> using the specified values.
308 * @param factory the (possibly <tt>null</tt>)PoolableObjectFactory to use to create, validate and destroy objects
309 * @param maxActive the maximum number of objects that can be borrowed from me at one time (see {@link #setMaxActive})
310 * @param whenExhaustedAction the action to take when the pool is exhausted (see {@link #getWhenExhaustedAction})
311 * @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})
312 */
313 public GenericObjectPool(PoolableObjectFactory factory, int maxActive, byte whenExhaustedAction, long maxWait) {
314 this(factory,maxActive,whenExhaustedAction,maxWait,DEFAULT_MAX_IDLE,DEFAULT_MIN_IDLE,DEFAULT_TEST_ON_BORROW,DEFAULT_TEST_ON_RETURN,DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS,DEFAULT_NUM_TESTS_PER_EVICTION_RUN,DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS,DEFAULT_TEST_WHILE_IDLE);
315 }
316
317 /***
318 * Create a new <tt>GenericObjectPool</tt> using the specified values.
319 * @param factory the (possibly <tt>null</tt>)PoolableObjectFactory to use to create, validate and destroy objects
320 * @param maxActive the maximum number of objects that can be borrowed from me at one time (see {@link #setMaxActive})
321 * @param whenExhaustedAction the action to take when the pool is exhausted (see {@link #getWhenExhaustedAction})
322 * @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})
323 * @param testOnBorrow whether or not to validate objects before they are returned by the {@link #borrowObject} method (see {@link #getTestOnBorrow})
324 * @param testOnReturn whether or not to validate objects after they are returned to the {@link #returnObject} method (see {@link #getTestOnReturn})
325 */
326 public GenericObjectPool(PoolableObjectFactory factory, int maxActive, byte whenExhaustedAction, long maxWait, boolean testOnBorrow, boolean testOnReturn) {
327 this(factory,maxActive,whenExhaustedAction,maxWait,DEFAULT_MAX_IDLE,DEFAULT_MIN_IDLE,testOnBorrow,testOnReturn,DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS,DEFAULT_NUM_TESTS_PER_EVICTION_RUN,DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS,DEFAULT_TEST_WHILE_IDLE);
328 }
329
330 /***
331 * Create a new <tt>GenericObjectPool</tt> using the specified values.
332 * @param factory the (possibly <tt>null</tt>)PoolableObjectFactory to use to create, validate and destroy objects
333 * @param maxActive the maximum number of objects that can be borrowed from me at one time (see {@link #setMaxActive})
334 * @param whenExhaustedAction the action to take when the pool is exhausted (see {@link #getWhenExhaustedAction})
335 * @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})
336 * @param maxIdle the maximum number of idle objects in my pool (see {@link #getMaxIdle})
337 */
338 public GenericObjectPool(PoolableObjectFactory factory, int maxActive, byte whenExhaustedAction, long maxWait, int maxIdle) {
339 this(factory,maxActive,whenExhaustedAction,maxWait,maxIdle,DEFAULT_MIN_IDLE,DEFAULT_TEST_ON_BORROW,DEFAULT_TEST_ON_RETURN,DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS,DEFAULT_NUM_TESTS_PER_EVICTION_RUN,DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS,DEFAULT_TEST_WHILE_IDLE);
340 }
341
342 /***
343 * Create a new <tt>GenericObjectPool</tt> using the specified values.
344 * @param factory the (possibly <tt>null</tt>)PoolableObjectFactory to use to create, validate and destroy objects
345 * @param maxActive the maximum number of objects that can be borrowed from me at one time (see {@link #setMaxActive})
346 * @param whenExhaustedAction the action to take when the pool is exhausted (see {@link #getWhenExhaustedAction})
347 * @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})
348 * @param maxIdle the maximum number of idle objects in my pool (see {@link #getMaxIdle})
349 * @param testOnBorrow whether or not to validate objects before they are returned by the {@link #borrowObject} method (see {@link #getTestOnBorrow})
350 * @param testOnReturn whether or not to validate objects after they are returned to the {@link #returnObject} method (see {@link #getTestOnReturn})
351 */
352 public GenericObjectPool(PoolableObjectFactory factory, int maxActive, byte whenExhaustedAction, long maxWait, int maxIdle, boolean testOnBorrow, boolean testOnReturn) {
353 this(factory,maxActive,whenExhaustedAction,maxWait,maxIdle,DEFAULT_MIN_IDLE,testOnBorrow,testOnReturn,DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS,DEFAULT_NUM_TESTS_PER_EVICTION_RUN,DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS,DEFAULT_TEST_WHILE_IDLE);
354 }
355
356 /***
357 * Create a new <tt>GenericObjectPool</tt> using the specified values.
358 * @param factory the (possibly <tt>null</tt>)PoolableObjectFactory to use to create, validate and destroy objects
359 * @param maxActive the maximum number of objects that can be borrowed from me at one time (see {@link #setMaxActive})
360 * @param whenExhaustedAction the action to take when the pool is exhausted (see {@link #setWhenExhaustedAction})
361 * @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})
362 * @param maxIdle the maximum number of idle objects in my pool (see {@link #setMaxIdle})
363 * @param testOnBorrow whether or not to validate objects before they are returned by the {@link #borrowObject} method (see {@link #setTestOnBorrow})
364 * @param testOnReturn whether or not to validate objects after they are returned to the {@link #returnObject} method (see {@link #setTestOnReturn})
365 * @param timeBetweenEvictionRunsMillis the amount of time (in milliseconds) to sleep between examining idle objects for eviction (see {@link #setTimeBetweenEvictionRunsMillis})
366 * @param numTestsPerEvictionRun the number of idle objects to examine per run within the idle object eviction thread (if any) (see {@link #setNumTestsPerEvictionRun})
367 * @param minEvictableIdleTimeMillis the minimum number of milliseconds an object can sit idle in the pool before it is eligable for evcition (see {@link #setMinEvictableIdleTimeMillis})
368 * @param testWhileIdle whether or not to validate objects in the idle object eviction thread, if any (see {@link #setTestWhileIdle})
369 */
370 public GenericObjectPool(PoolableObjectFactory factory, int maxActive, byte whenExhaustedAction, long maxWait, int maxIdle, boolean testOnBorrow, boolean testOnReturn, long timeBetweenEvictionRunsMillis, int numTestsPerEvictionRun, long minEvictableIdleTimeMillis, boolean testWhileIdle) {
371 this(factory, maxActive, whenExhaustedAction, maxWait, maxIdle, DEFAULT_MIN_IDLE, testOnBorrow, testOnReturn, timeBetweenEvictionRunsMillis, numTestsPerEvictionRun, minEvictableIdleTimeMillis, testWhileIdle);
372 }
373
374 /***
375 * Create a new <tt>GenericObjectPool</tt> using the specified values.
376 * @param factory the (possibly <tt>null</tt>)PoolableObjectFactory to use to create, validate and destroy objects
377 * @param maxActive the maximum number of objects that can be borrowed from me at one time (see {@link #setMaxActive})
378 * @param whenExhaustedAction the action to take when the pool is exhausted (see {@link #setWhenExhaustedAction})
379 * @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})
380 * @param maxIdle the maximum number of idle objects in my pool (see {@link #setMaxIdle})
381 * @param minIdle the minimum number of idle objects in my pool (see {@link #setMinIdle})
382 * @param testOnBorrow whether or not to validate objects before they are returned by the {@link #borrowObject} method (see {@link #setTestOnBorrow})
383 * @param testOnReturn whether or not to validate objects after they are returned to the {@link #returnObject} method (see {@link #setTestOnReturn})
384 * @param timeBetweenEvictionRunsMillis the amount of time (in milliseconds) to sleep between examining idle objects for eviction (see {@link #setTimeBetweenEvictionRunsMillis})
385 * @param numTestsPerEvictionRun the number of idle objects to examine per run within the idle object eviction thread (if any) (see {@link #setNumTestsPerEvictionRun})
386 * @param minEvictableIdleTimeMillis the minimum number of milliseconds an object can sit idle in the pool before it is eligable for evcition (see {@link #setMinEvictableIdleTimeMillis})
387 * @param testWhileIdle whether or not to validate objects in the idle object eviction thread, if any (see {@link #setTestWhileIdle})
388 */
389 public GenericObjectPool(PoolableObjectFactory factory, int maxActive, byte whenExhaustedAction, long maxWait, int maxIdle, int minIdle, boolean testOnBorrow, boolean testOnReturn, long timeBetweenEvictionRunsMillis, int numTestsPerEvictionRun, long minEvictableIdleTimeMillis, boolean testWhileIdle) {
390 this(factory, maxActive, whenExhaustedAction, maxWait, maxIdle, minIdle, testOnBorrow, testOnReturn, timeBetweenEvictionRunsMillis, numTestsPerEvictionRun, minEvictableIdleTimeMillis, testWhileIdle, DEFAULT_SOFT_MIN_EVICTABLE_IDLE_TIME_MILLIS);
391 }
392
393 /***
394 * Create a new <tt>GenericObjectPool</tt> using the specified values.
395 * @param factory the (possibly <tt>null</tt>)PoolableObjectFactory to use to create, validate and destroy objects
396 * @param maxActive the maximum number of objects that can be borrowed from me at one time (see {@link #setMaxActive})
397 * @param whenExhaustedAction the action to take when the pool is exhausted (see {@link #setWhenExhaustedAction})
398 * @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})
399 * @param maxIdle the maximum number of idle objects in my pool (see {@link #setMaxIdle})
400 * @param minIdle the minimum number of idle objects in my pool (see {@link #setMinIdle})
401 * @param testOnBorrow whether or not to validate objects before they are returned by the {@link #borrowObject} method (see {@link #setTestOnBorrow})
402 * @param testOnReturn whether or not to validate objects after they are returned to the {@link #returnObject} method (see {@link #setTestOnReturn})
403 * @param timeBetweenEvictionRunsMillis the amount of time (in milliseconds) to sleep between examining idle objects for eviction (see {@link #setTimeBetweenEvictionRunsMillis})
404 * @param numTestsPerEvictionRun the number of idle objects to examine per run within the idle object eviction thread (if any) (see {@link #setNumTestsPerEvictionRun})
405 * @param minEvictableIdleTimeMillis the minimum number of milliseconds an object can sit idle in the pool before it is eligable for evcition (see {@link #setMinEvictableIdleTimeMillis})
406 * @param testWhileIdle whether or not to validate objects in the idle object eviction thread, if any (see {@link #setTestWhileIdle})
407 * @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})
408 */
409 public GenericObjectPool(PoolableObjectFactory factory, int maxActive, byte whenExhaustedAction, long maxWait, int maxIdle, int minIdle, boolean testOnBorrow, boolean testOnReturn, long timeBetweenEvictionRunsMillis, int numTestsPerEvictionRun, long minEvictableIdleTimeMillis, boolean testWhileIdle, long softMinEvictableIdleTimeMillis) {
410 _factory = factory;
411 _maxActive = maxActive;
412 switch(whenExhaustedAction) {
413 case WHEN_EXHAUSTED_BLOCK:
414 case WHEN_EXHAUSTED_FAIL:
415 case WHEN_EXHAUSTED_GROW:
416 _whenExhaustedAction = whenExhaustedAction;
417 break;
418 default:
419 throw new IllegalArgumentException("whenExhaustedAction " + whenExhaustedAction + " not recognized.");
420 }
421 _maxWait = maxWait;
422 _maxIdle = maxIdle;
423 _minIdle = minIdle;
424 _testOnBorrow = testOnBorrow;
425 _testOnReturn = testOnReturn;
426 _timeBetweenEvictionRunsMillis = timeBetweenEvictionRunsMillis;
427 _numTestsPerEvictionRun = numTestsPerEvictionRun;
428 _minEvictableIdleTimeMillis = minEvictableIdleTimeMillis;
429 _softMinEvictableIdleTimeMillis = softMinEvictableIdleTimeMillis;
430 _testWhileIdle = testWhileIdle;
431
432 _pool = new LinkedList();
433 startEvictor(_timeBetweenEvictionRunsMillis);
434 }
435
436
437
438
439
440 /***
441 * Returns the cap on the total number of active instances from my pool.
442 * @return the cap on the total number of active instances from my pool.
443 * @see #setMaxActive
444 */
445 public synchronized int getMaxActive() {
446 return _maxActive;
447 }
448
449 /***
450 * Sets the cap on the total number of active instances from my pool.
451 * @param maxActive The cap on the total number of active instances from my pool.
452 * Use a negative value for an infinite number of instances.
453 * @see #getMaxActive
454 */
455 public synchronized void setMaxActive(int maxActive) {
456 _maxActive = maxActive;
457 notifyAll();
458 }
459
460 /***
461 * Returns the action to take when the {@link #borrowObject} method
462 * is invoked when the pool is exhausted (the maximum number
463 * of "active" objects has been reached).
464 *
465 * @return one of {@link #WHEN_EXHAUSTED_BLOCK}, {@link #WHEN_EXHAUSTED_FAIL} or {@link #WHEN_EXHAUSTED_GROW}
466 * @see #setWhenExhaustedAction
467 */
468 public synchronized byte getWhenExhaustedAction() {
469 return _whenExhaustedAction;
470 }
471
472 /***
473 * Sets the action to take when the {@link #borrowObject} method
474 * is invoked when the pool is exhausted (the maximum number
475 * of "active" objects has been reached).
476 *
477 * @param whenExhaustedAction the action code, which must be one of
478 * {@link #WHEN_EXHAUSTED_BLOCK}, {@link #WHEN_EXHAUSTED_FAIL},
479 * or {@link #WHEN_EXHAUSTED_GROW}
480 * @see #getWhenExhaustedAction
481 */
482 public synchronized void setWhenExhaustedAction(byte whenExhaustedAction) {
483 switch(whenExhaustedAction) {
484 case WHEN_EXHAUSTED_BLOCK:
485 case WHEN_EXHAUSTED_FAIL:
486 case WHEN_EXHAUSTED_GROW:
487 _whenExhaustedAction = whenExhaustedAction;
488 notifyAll();
489 break;
490 default:
491 throw new IllegalArgumentException("whenExhaustedAction " + whenExhaustedAction + " not recognized.");
492 }
493 }
494
495
496 /***
497 * Returns the maximum amount of time (in milliseconds) the
498 * {@link #borrowObject} method should block before throwing
499 * an exception when the pool is exhausted and the
500 * {@link #setWhenExhaustedAction "when exhausted" action} is
501 * {@link #WHEN_EXHAUSTED_BLOCK}.
502 *
503 * When less than 0, the {@link #borrowObject} method
504 * may block indefinitely.
505 *
506 * @see #setMaxWait
507 * @see #setWhenExhaustedAction
508 * @see #WHEN_EXHAUSTED_BLOCK
509 */
510 public synchronized long getMaxWait() {
511 return _maxWait;
512 }
513
514 /***
515 * Sets the maximum amount of time (in milliseconds) the
516 * {@link #borrowObject} method should block before throwing
517 * an exception when the pool is exhausted and the
518 * {@link #setWhenExhaustedAction "when exhausted" action} is
519 * {@link #WHEN_EXHAUSTED_BLOCK}.
520 *
521 * When less than 0, the {@link #borrowObject} method
522 * may block indefinitely.
523 *
524 * @see #getMaxWait
525 * @see #setWhenExhaustedAction
526 * @see #WHEN_EXHAUSTED_BLOCK
527 */
528 public synchronized void setMaxWait(long maxWait) {
529 _maxWait = maxWait;
530 notifyAll();
531 }
532
533 /***
534 * Returns the cap on the number of "idle" instances in the pool.
535 * @return the cap on the number of "idle" instances in the pool.
536 * @see #setMaxIdle
537 */
538 public synchronized int getMaxIdle() {
539 return _maxIdle;
540 }
541
542 /***
543 * Sets the cap on the number of "idle" instances in the pool.
544 * @param maxIdle The cap on the number of "idle" instances in the pool.
545 * Use a negative value to indicate an unlimited number
546 * of idle instances.
547 * @see #getMaxIdle
548 */
549 public synchronized void setMaxIdle(int maxIdle) {
550 _maxIdle = maxIdle;
551 notifyAll();
552 }
553
554 /***
555 * Sets the minimum number of objects allowed in the pool
556 * before the evictor thread (if active) spawns new objects.
557 * (Note no objects are created when: numActive + numIdle >= maxActive)
558 *
559 * @param minIdle The minimum number of objects.
560 * @see #getMinIdle
561 */
562 public synchronized void setMinIdle(int minIdle) {
563 _minIdle = minIdle;
564 notifyAll();
565 }
566
567 /***
568 * Returns the minimum number of objects allowed in the pool
569 * before the evictor thread (if active) spawns new objects.
570 * (Note no objects are created when: numActive + numIdle >= maxActive)
571 *
572 * @return The minimum number of objects.
573 * @see #setMinIdle
574 */
575 public synchronized int getMinIdle() {
576 return _minIdle;
577 }
578
579 /***
580 * When <tt>true</tt>, objects will be
581 * {@link PoolableObjectFactory#validateObject validated}
582 * before being returned by the {@link #borrowObject}
583 * method. If the object fails to validate,
584 * it will be dropped from the pool, and we will attempt
585 * to borrow another.
586 *
587 * @see #setTestOnBorrow
588 */
589 public synchronized boolean getTestOnBorrow() {
590 return _testOnBorrow;
591 }
592
593 /***
594 * When <tt>true</tt>, objects will be
595 * {@link PoolableObjectFactory#validateObject validated}
596 * before being returned by the {@link #borrowObject}
597 * method. If the object fails to validate,
598 * it will be dropped from the pool, and we will attempt
599 * to borrow another.
600 *
601 * @see #getTestOnBorrow
602 */
603 public synchronized void setTestOnBorrow(boolean testOnBorrow) {
604 _testOnBorrow = testOnBorrow;
605 }
606
607 /***
608 * When <tt>true</tt>, objects will be
609 * {@link PoolableObjectFactory#validateObject validated}
610 * before being returned to the pool within the
611 * {@link #returnObject}.
612 *
613 * @see #setTestOnReturn
614 */
615 public synchronized boolean getTestOnReturn() {
616 return _testOnReturn;
617 }
618
619 /***
620 * When <tt>true</tt>, objects will be
621 * {@link PoolableObjectFactory#validateObject validated}
622 * before being returned to the pool within the
623 * {@link #returnObject}.
624 *
625 * @see #getTestOnReturn
626 */
627 public synchronized void setTestOnReturn(boolean testOnReturn) {
628 _testOnReturn = testOnReturn;
629 }
630
631 /***
632 * Returns the number of milliseconds to sleep between runs of the
633 * idle object evictor thread.
634 * When non-positive, no idle object evictor thread will be
635 * run.
636 *
637 * @see #setTimeBetweenEvictionRunsMillis
638 */
639 public synchronized long getTimeBetweenEvictionRunsMillis() {
640 return _timeBetweenEvictionRunsMillis;
641 }
642
643 /***
644 * Sets the number of milliseconds to sleep between runs of the
645 * idle object evictor thread.
646 * When non-positive, no idle object evictor thread will be
647 * run.
648 *
649 * @see #getTimeBetweenEvictionRunsMillis
650 */
651 public synchronized void setTimeBetweenEvictionRunsMillis(long timeBetweenEvictionRunsMillis) {
652 _timeBetweenEvictionRunsMillis = timeBetweenEvictionRunsMillis;
653 startEvictor(_timeBetweenEvictionRunsMillis);
654 }
655
656 /***
657 * Returns the max number of objects to examine during each run of the
658 * idle object evictor thread (if any).
659 *
660 * @see #setNumTestsPerEvictionRun
661 * @see #setTimeBetweenEvictionRunsMillis
662 */
663 public synchronized int getNumTestsPerEvictionRun() {
664 return _numTestsPerEvictionRun;
665 }
666
667 /***
668 * Sets the max number of objects to examine during each run of the
669 * idle object evictor thread (if any).
670 * <p>
671 * When a negative value is supplied, <tt>ceil({@link #getNumIdle})/abs({@link #getNumTestsPerEvictionRun})</tt>
672 * tests will be run. I.e., when the value is <i>-n</i>, roughly one <i>n</i>th of the
673 * idle objects will be tested per run.
674 *
675 * @see #getNumTestsPerEvictionRun
676 * @see #setTimeBetweenEvictionRunsMillis
677 */
678 public synchronized void setNumTestsPerEvictionRun(int numTestsPerEvictionRun) {
679 _numTestsPerEvictionRun = numTestsPerEvictionRun;
680 }
681
682 /***
683 * Returns the minimum amount of time an object may sit idle in the pool
684 * before it is eligable for eviction by the idle object evictor
685 * (if any).
686 *
687 * @see #setMinEvictableIdleTimeMillis
688 * @see #setTimeBetweenEvictionRunsMillis
689 */
690 public synchronized long getMinEvictableIdleTimeMillis() {
691 return _minEvictableIdleTimeMillis;
692 }
693
694 /***
695 * Sets the minimum amount of time an object may sit idle in the pool
696 * before it is eligable for eviction by the idle object evictor
697 * (if any).
698 * When non-positive, no objects will be evicted from the pool
699 * due to idle time alone.
700 *
701 * @see #getMinEvictableIdleTimeMillis
702 * @see #setTimeBetweenEvictionRunsMillis
703 */
704 public synchronized void setMinEvictableIdleTimeMillis(long minEvictableIdleTimeMillis) {
705 _minEvictableIdleTimeMillis = minEvictableIdleTimeMillis;
706 }
707
708 /***
709 * Returns the minimum amount of time an object may sit idle in the pool
710 * before it is eligable for eviction by the idle object evictor
711 * (if any), with the extra condition that at least
712 * "minIdle" amount of object remain in the pool.
713 *
714 * @see #setSoftMinEvictableIdleTimeMillis
715 */
716 public synchronized long getSoftMinEvictableIdleTimeMillis() {
717 return _softMinEvictableIdleTimeMillis;
718 }
719
720 /***
721 * Sets the minimum amount of time an object may sit idle in the pool
722 * before it is eligable for eviction by the idle object evictor
723 * (if any), with the extra condition that at least
724 * "minIdle" amount of object remain in the pool.
725 * When non-positive, no objects will be evicted from the pool
726 * due to idle time alone.
727 *
728 * @see #getSoftMinEvictableIdleTimeMillis
729 */
730 public synchronized void setSoftMinEvictableIdleTimeMillis(long softMinEvictableIdleTimeMillis) {
731 _softMinEvictableIdleTimeMillis = softMinEvictableIdleTimeMillis;
732 }
733
734 /***
735 * When <tt>true</tt>, objects will be
736 * {@link PoolableObjectFactory#validateObject validated}
737 * by the idle object evictor (if any). If an object
738 * fails to validate, it will be dropped from the pool.
739 *
740 * @see #setTestWhileIdle
741 * @see #setTimeBetweenEvictionRunsMillis
742 */
743 public synchronized boolean getTestWhileIdle() {
744 return _testWhileIdle;
745 }
746
747 /***
748 * When <tt>true</tt>, objects will be
749 * {@link PoolableObjectFactory#validateObject validated}
750 * by the idle object evictor (if any). If an object
751 * fails to validate, it will be dropped from the pool.
752 *
753 * @see #getTestWhileIdle
754 * @see #setTimeBetweenEvictionRunsMillis
755 */
756 public synchronized void setTestWhileIdle(boolean testWhileIdle) {
757 _testWhileIdle = testWhileIdle;
758 }
759
760 /***
761 * Sets my configuration.
762 * @see GenericObjectPool.Config
763 */
764 public synchronized void setConfig(GenericObjectPool.Config conf) {
765 setMaxIdle(conf.maxIdle);
766 setMinIdle(conf.minIdle);
767 setMaxActive(conf.maxActive);
768 setMaxWait(conf.maxWait);
769 setWhenExhaustedAction(conf.whenExhaustedAction);
770 setTestOnBorrow(conf.testOnBorrow);
771 setTestOnReturn(conf.testOnReturn);
772 setTestWhileIdle(conf.testWhileIdle);
773 setNumTestsPerEvictionRun(conf.numTestsPerEvictionRun);
774 setMinEvictableIdleTimeMillis(conf.minEvictableIdleTimeMillis);
775 setTimeBetweenEvictionRunsMillis(conf.timeBetweenEvictionRunsMillis);
776 notifyAll();
777 }
778
779
780
781 public synchronized Object borrowObject() throws Exception {
782 assertOpen();
783 long starttime = System.currentTimeMillis();
784 for(;;) {
785 ObjectTimestampPair pair = null;
786
787
788 try {
789 pair = (ObjectTimestampPair)(_pool.removeFirst());
790 } catch(NoSuchElementException e) {
791 ;
792 }
793
794
795 if(null == pair) {
796
797
798 if(_maxActive < 0 || _numActive < _maxActive) {
799
800 } else {
801
802 switch(_whenExhaustedAction) {
803 case WHEN_EXHAUSTED_GROW:
804
805 break;
806 case WHEN_EXHAUSTED_FAIL:
807 throw new NoSuchElementException("Pool exhausted");
808 case WHEN_EXHAUSTED_BLOCK:
809 try {
810 if(_maxWait <= 0) {
811 wait();
812 } else {
813
814
815 final long elapsed = (System.currentTimeMillis() - starttime);
816 final long waitTime = _maxWait - elapsed;
817 if (waitTime > 0)
818 {
819 wait(waitTime);
820 }
821 }
822 } catch(InterruptedException e) {
823
824 }
825 if(_maxWait > 0 && ((System.currentTimeMillis() - starttime) >= _maxWait)) {
826 throw new NoSuchElementException("Timeout waiting for idle object");
827 } else {
828 continue;
829 }
830 default:
831 throw new IllegalArgumentException("WhenExhaustedAction property " + _whenExhaustedAction + " not recognized.");
832 }
833 }
834 }
835 _numActive++;
836
837
838 boolean newlyCreated = false;
839 if(null == pair) {
840 try {
841 Object obj = _factory.makeObject();
842 pair = new ObjectTimestampPair(obj);
843 newlyCreated = true;
844 } finally {
845 if (!newlyCreated) {
846
847 _numActive--;
848 notifyAll();
849 }
850 }
851 }
852
853
854 try {
855 _factory.activateObject(pair.value);
856 if(_testOnBorrow && !_factory.validateObject(pair.value)) {
857 throw new Exception("ValidateObject failed");
858 }
859 return pair.value;
860 }
861 catch (Throwable e) {
862
863 _numActive--;
864 notifyAll();
865 try {
866 _factory.destroyObject(pair.value);
867 }
868 catch (Throwable e2) {
869
870 }
871 if(newlyCreated) {
872 throw new NoSuchElementException("Could not create a validated object, cause: " + e.getMessage());
873 }
874 else {
875 continue;
876 }
877 }
878 }
879 }
880
881 public synchronized void invalidateObject(Object obj) throws Exception {
882 assertOpen();
883 try {
884 _factory.destroyObject(obj);
885 }
886 finally {
887 _numActive--;
888 notifyAll();
889 }
890 }
891
892 public synchronized void clear() {
893 assertOpen();
894 for(Iterator it = _pool.iterator(); it.hasNext(); ) {
895 try {
896 _factory.destroyObject(((ObjectTimestampPair)(it.next())).value);
897 } catch(Exception e) {
898
899 }
900 it.remove();
901 }
902 _pool.clear();
903 notifyAll();
904 }
905
906 public synchronized int getNumActive() {
907 assertOpen();
908 return _numActive;
909 }
910
911 public synchronized int getNumIdle() {
912 assertOpen();
913 return _pool.size();
914 }
915
916 public synchronized void returnObject(Object obj) throws Exception {
917 assertOpen();
918 addObjectToPool(obj, true);
919 }
920
921 private void addObjectToPool(Object obj, boolean decrementNumActive) throws Exception {
922 boolean success = true;
923 if(_testOnReturn && !(_factory.validateObject(obj))) {
924 success = false;
925 } else {
926 try {
927 _factory.passivateObject(obj);
928 } catch(Exception e) {
929 success = false;
930 }
931 }
932
933 boolean shouldDestroy = !success;
934
935 if (decrementNumActive) {
936 _numActive--;
937 }
938 if((_maxIdle >= 0) && (_pool.size() >= _maxIdle)) {
939 shouldDestroy = true;
940 } else if(success) {
941 _pool.addLast(new ObjectTimestampPair(obj));
942 }
943 notifyAll();
944
945 if(shouldDestroy) {
946 try {
947 _factory.destroyObject(obj);
948 } catch(Exception e) {
949
950 }
951 }
952 }
953
954 public synchronized void close() throws Exception {
955 clear();
956 _pool = null;
957 _factory = null;
958 startEvictor(-1L);
959 super.close();
960 }
961
962 public synchronized void setFactory(PoolableObjectFactory factory) throws IllegalStateException {
963 assertOpen();
964 if(0 < getNumActive()) {
965 throw new IllegalStateException("Objects are already active");
966 } else {
967 clear();
968 _factory = factory;
969 }
970 }
971
972 public synchronized void evict() throws Exception {
973 assertOpen();
974 if(!_pool.isEmpty()) {
975 ListIterator iter;
976 if (evictLastIndex < 0) {
977 iter = _pool.listIterator(_pool.size());
978 } else {
979 iter = _pool.listIterator(evictLastIndex);
980 }
981 for(int i=0,m=getNumTests();i<m;i++) {
982 if(!iter.hasPrevious()) {
983 iter = _pool.listIterator(_pool.size());
984 }
985 boolean removeObject = false;
986 final ObjectTimestampPair pair = (ObjectTimestampPair)(iter.previous());
987 final long idleTimeMilis = System.currentTimeMillis() - pair.tstamp;
988 if ((_minEvictableIdleTimeMillis > 0)
989 && (idleTimeMilis > _minEvictableIdleTimeMillis)) {
990 removeObject = true;
991 } else if ((_softMinEvictableIdleTimeMillis > 0)
992 && (idleTimeMilis > _softMinEvictableIdleTimeMillis)
993 && (getNumIdle() > getMinIdle())) {
994 removeObject = true;
995 }
996 if(_testWhileIdle && !removeObject) {
997 boolean active = false;
998 try {
999 _factory.activateObject(pair.value);
1000 active = true;
1001 } catch(Exception e) {
1002 removeObject=true;
1003 }
1004 if(active) {
1005 if(!_factory.validateObject(pair.value)) {
1006 removeObject=true;
1007 } else {
1008 try {
1009 _factory.passivateObject(pair.value);
1010 } catch(Exception e) {
1011 removeObject=true;
1012 }
1013 }
1014 }
1015 }
1016 if(removeObject) {
1017 try {
1018 iter.remove();
1019 _factory.destroyObject(pair.value);
1020 } catch(Exception e) {
1021
1022 }
1023 }
1024 }
1025 evictLastIndex = iter.previousIndex();
1026 }
1027 }
1028
1029 /***
1030 * Check to see if we are below our minimum number of objects
1031 * if so enough to bring us back to our minimum.
1032 */
1033 private void ensureMinIdle() throws Exception {
1034
1035
1036
1037
1038
1039 int objectDeficit = calculateDeficit();
1040 for ( int j = 0 ; j < objectDeficit && calculateDeficit() > 0 ; j++ ) {
1041 addObject();
1042 }
1043 }
1044
1045 private synchronized int calculateDeficit() {
1046 int objectDeficit = getMinIdle() - getNumIdle();
1047 if (_maxActive > 0) {
1048 int growLimit = Math.max(0, getMaxActive() - getNumActive() - getNumIdle());
1049 objectDeficit = Math.min(objectDeficit, growLimit);
1050 }
1051 return objectDeficit;
1052 }
1053
1054 /***
1055 * Create an object, and place it into the pool.
1056 * addObject() is useful for "pre-loading" a pool with idle objects.
1057 */
1058 public synchronized void addObject() throws Exception {
1059 assertOpen();
1060 Object obj = _factory.makeObject();
1061 addObjectToPool(obj, false);
1062 }
1063
1064
1065
1066 /***
1067 * Start the eviction thread or service, or when
1068 * <i>delay</i> is non-positive, stop it
1069 * if it is already running.
1070 */
1071 protected synchronized void startEvictor(long delay) {
1072 if(null != _evictor) {
1073 _evictor.cancel();
1074 _evictor = null;
1075 }
1076 if(delay > 0) {
1077 _evictor = new Evictor();
1078 EVICTION_TIMER.schedule(_evictor, delay, delay);
1079 }
1080 }
1081
1082 synchronized String debugInfo() {
1083 StringBuffer buf = new StringBuffer();
1084 buf.append("Active: ").append(getNumActive()).append("\n");
1085 buf.append("Idle: ").append(getNumIdle()).append("\n");
1086 buf.append("Idle Objects:\n");
1087 Iterator it = _pool.iterator();
1088 long time = System.currentTimeMillis();
1089 while(it.hasNext()) {
1090 ObjectTimestampPair pair = (ObjectTimestampPair)(it.next());
1091 buf.append("\t").append(pair.value).append("\t").append(time - pair.tstamp).append("\n");
1092 }
1093 return buf.toString();
1094 }
1095
1096 private int getNumTests() {
1097 if(_numTestsPerEvictionRun >= 0) {
1098 return Math.min(_numTestsPerEvictionRun, _pool.size());
1099 } else {
1100 return(int)(Math.ceil((double)_pool.size()/Math.abs((double)_numTestsPerEvictionRun)));
1101 }
1102 }
1103
1104
1105
1106 /***
1107 * The idle object evictor {@link TimerTask}.
1108 * @see GenericObjectPool#setTimeBetweenEvictionRunsMillis
1109 */
1110 private class Evictor extends TimerTask {
1111 public void run() {
1112 try {
1113 evict();
1114 } catch(Exception e) {
1115
1116 }
1117 try {
1118 ensureMinIdle();
1119 } catch(Exception e) {
1120
1121 }
1122 }
1123 }
1124
1125 /***
1126 * A simple "struct" encapsulating the
1127 * configuration information for a {@link GenericObjectPool}.
1128 * @see GenericObjectPool#GenericObjectPool(org.apache.commons.pool.PoolableObjectFactory,org.apache.commons.pool.impl.GenericObjectPool.Config)
1129 * @see GenericObjectPool#setConfig
1130 */
1131 public static class Config {
1132 public int maxIdle = GenericObjectPool.DEFAULT_MAX_IDLE;
1133 public int minIdle = GenericObjectPool.DEFAULT_MIN_IDLE;
1134 public int maxActive = GenericObjectPool.DEFAULT_MAX_ACTIVE;
1135 public long maxWait = GenericObjectPool.DEFAULT_MAX_WAIT;
1136 public byte whenExhaustedAction = GenericObjectPool.DEFAULT_WHEN_EXHAUSTED_ACTION;
1137 public boolean testOnBorrow = GenericObjectPool.DEFAULT_TEST_ON_BORROW;
1138 public boolean testOnReturn = GenericObjectPool.DEFAULT_TEST_ON_RETURN;
1139 public boolean testWhileIdle = GenericObjectPool.DEFAULT_TEST_WHILE_IDLE;
1140 public long timeBetweenEvictionRunsMillis = GenericObjectPool.DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS;
1141 public int numTestsPerEvictionRun = GenericObjectPool.DEFAULT_NUM_TESTS_PER_EVICTION_RUN;
1142 public long minEvictableIdleTimeMillis = GenericObjectPool.DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS;
1143 public long softMinEvictableIdleTimeMillis = GenericObjectPool.DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS;
1144 }
1145
1146
1147
1148 /***
1149 * The cap on the number of idle instances in the pool.
1150 * @see #setMaxIdle
1151 * @see #getMaxIdle
1152 */
1153 private int _maxIdle = DEFAULT_MAX_IDLE;
1154
1155 /***
1156 * The cap on the minimum number of idle instances in the pool.
1157 * @see #setMinIdle
1158 * @see #getMinIdle
1159 */
1160 private int _minIdle = DEFAULT_MIN_IDLE;
1161
1162 /***
1163 * The cap on the total number of active instances from the pool.
1164 * @see #setMaxActive
1165 * @see #getMaxActive
1166 */
1167 protected int _maxActive = DEFAULT_MAX_ACTIVE;
1168
1169 /***
1170 * The maximum amount of time (in millis) the
1171 * {@link #borrowObject} method should block before throwing
1172 * an exception when the pool is exhausted and the
1173 * {@link #getWhenExhaustedAction "when exhausted" action} is
1174 * {@link #WHEN_EXHAUSTED_BLOCK}.
1175 *
1176 * When less than 0, the {@link #borrowObject} method
1177 * may block indefinitely.
1178 *
1179 * @see #setMaxWait
1180 * @see #getMaxWait
1181 * @see #WHEN_EXHAUSTED_BLOCK
1182 * @see #setWhenExhaustedAction
1183 * @see #getWhenExhaustedAction
1184 */
1185 protected long _maxWait = DEFAULT_MAX_WAIT;
1186
1187 /***
1188 * The action to take when the {@link #borrowObject} method
1189 * is invoked when the pool is exhausted (the maximum number
1190 * of "active" objects has been reached).
1191 *
1192 * @see #WHEN_EXHAUSTED_BLOCK
1193 * @see #WHEN_EXHAUSTED_FAIL
1194 * @see #WHEN_EXHAUSTED_GROW
1195 * @see #DEFAULT_WHEN_EXHAUSTED_ACTION
1196 * @see #setWhenExhaustedAction
1197 * @see #getWhenExhaustedAction
1198 */
1199 protected byte _whenExhaustedAction = DEFAULT_WHEN_EXHAUSTED_ACTION;
1200
1201 /***
1202 * When <tt>true</tt>, objects will be
1203 * {@link PoolableObjectFactory#validateObject validated}
1204 * before being returned by the {@link #borrowObject}
1205 * method. If the object fails to validate,
1206 * it will be dropped from the pool, and we will attempt
1207 * to borrow another.
1208 *
1209 * @see #setTestOnBorrow
1210 * @see #getTestOnBorrow
1211 */
1212 protected boolean _testOnBorrow = DEFAULT_TEST_ON_BORROW;
1213
1214 /***
1215 * When <tt>true</tt>, objects will be
1216 * {@link PoolableObjectFactory#validateObject validated}
1217 * before being returned to the pool within the
1218 * {@link #returnObject}.
1219 *
1220 * @see #getTestOnReturn
1221 * @see #setTestOnReturn
1222 */
1223 private boolean _testOnReturn = DEFAULT_TEST_ON_RETURN;
1224
1225 /***
1226 * When <tt>true</tt>, objects will be
1227 * {@link PoolableObjectFactory#validateObject validated}
1228 * by the idle object evictor (if any). If an object
1229 * fails to validate, it will be dropped from the pool.
1230 *
1231 * @see #setTestWhileIdle
1232 * @see #getTestWhileIdle
1233 * @see #getTimeBetweenEvictionRunsMillis
1234 * @see #setTimeBetweenEvictionRunsMillis
1235 */
1236 private boolean _testWhileIdle = DEFAULT_TEST_WHILE_IDLE;
1237
1238 /***
1239 * The number of milliseconds to sleep between runs of the
1240 * idle object evictor thread.
1241 * When non-positive, no idle object evictor thread will be
1242 * run.
1243 *
1244 * @see #setTimeBetweenEvictionRunsMillis
1245 * @see #getTimeBetweenEvictionRunsMillis
1246 */
1247 private long _timeBetweenEvictionRunsMillis = DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS;
1248
1249 /***
1250 * The max number of objects to examine during each run of the
1251 * idle object evictor thread (if any).
1252 * <p>
1253 * When a negative value is supplied, <tt>ceil({@link #getNumIdle})/abs({@link #getNumTestsPerEvictionRun})</tt>
1254 * tests will be run. I.e., when the value is <i>-n</i>, roughly one <i>n</i>th of the
1255 * idle objects will be tested per run.
1256 *
1257 * @see #setNumTestsPerEvictionRun
1258 * @see #getNumTestsPerEvictionRun
1259 * @see #getTimeBetweenEvictionRunsMillis
1260 * @see #setTimeBetweenEvictionRunsMillis
1261 */
1262 private int _numTestsPerEvictionRun = DEFAULT_NUM_TESTS_PER_EVICTION_RUN;
1263
1264 /***
1265 * The minimum amount of time an object may sit idle in the pool
1266 * before it is eligable for eviction by the idle object evictor
1267 * (if any).
1268 * When non-positive, no objects will be evicted from the pool
1269 * due to idle time alone.
1270 *
1271 * @see #setMinEvictableIdleTimeMillis
1272 * @see #getMinEvictableIdleTimeMillis
1273 * @see #getTimeBetweenEvictionRunsMillis
1274 * @see #setTimeBetweenEvictionRunsMillis
1275 */
1276 private long _minEvictableIdleTimeMillis = DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS;
1277
1278 /***
1279 * The minimum amount of time an object may sit idle in the pool
1280 * before it is eligable for eviction by the idle object evictor
1281 * (if any), with the extra condition that at least
1282 * "minIdle" amount of object remain in the pool.
1283 * When non-positive, no objects will be evicted from the pool
1284 * due to idle time alone.
1285 *
1286 * @see #setSoftMinEvictableIdleTimeMillis
1287 * @see #getSoftMinEvictableIdleTimeMillis
1288 */
1289 private long _softMinEvictableIdleTimeMillis = DEFAULT_SOFT_MIN_EVICTABLE_IDLE_TIME_MILLIS;
1290
1291 /*** My pool. */
1292 protected LinkedList _pool = null;
1293
1294 /*** My {@link PoolableObjectFactory}. */
1295 protected PoolableObjectFactory _factory = null;
1296
1297 /***
1298 * The number of objects {@link #borrowObject} borrowed
1299 * from the pool, but not yet returned.
1300 */
1301 protected int _numActive = 0;
1302
1303 /***
1304 * My idle object eviction {@link TimerTask}, if any.
1305 */
1306 private Evictor _evictor = null;
1307
1308 /***
1309 * Position in the _pool where the _evictor last stopped.
1310 */
1311 private int evictLastIndex = -1;
1312 }