001: /*
002: * $Id: CommonsPoolObjectPool.java 11376 2008-03-16 17:44:10Z dfeist $
003: * --------------------------------------------------------------------------------------
004: * Copyright (c) MuleSource, Inc. All rights reserved. http://www.mulesource.com
005: *
006: * The software in this package is published under the terms of the CPAL v1.0
007: * license, a copy of which has been included with this distribution in the
008: * LICENSE.txt file.
009: */
010:
011: package org.mule.util.pool;
012:
013: import org.mule.api.lifecycle.Disposable;
014: import org.mule.api.lifecycle.Initialisable;
015: import org.mule.api.lifecycle.InitialisationException;
016: import org.mule.api.lifecycle.LifecycleTransitionResult;
017: import org.mule.api.object.ObjectFactory;
018: import org.mule.config.PoolingProfile;
019: import org.mule.config.i18n.MessageFactory;
020:
021: import java.util.ArrayList;
022: import java.util.List;
023:
024: import org.apache.commons.logging.Log;
025: import org.apache.commons.logging.LogFactory;
026: import org.apache.commons.pool.PoolableObjectFactory;
027: import org.apache.commons.pool.impl.GenericObjectPool;
028:
029: /**
030: * <code>CommonsPoolProxyPool</code> is an implementation of {@link ObjectPool}
031: * that internally uses the commons-pool {@link GenericObjectPool} and uses a
032: * {@link ObjectFactory} for creating new pooled instances.
033: */
034: public class CommonsPoolObjectPool implements ObjectPool,
035: Initialisable, Disposable {
036: /**
037: * logger used by this class
038: */
039: protected static final Log logger = LogFactory
040: .getLog(CommonsPoolObjectPool.class);
041:
042: /**
043: * The pool
044: */
045: protected GenericObjectPool pool;
046:
047: /**
048: * The ObjectFactory used to create new pool instances
049: */
050: protected ObjectFactory objectFactory;
051:
052: /**
053: * The pooling profile used to configure and initialise pool
054: */
055: protected PoolingProfile poolingProfile;
056:
057: /**
058: * Creates a new pool and an Object factory with the UMODescriptor
059: *
060: * @param descriptor the descriptor to use when constructing MuleProxy objects in
061: * the pool
062: */
063: public CommonsPoolObjectPool(ObjectFactory objectFactory,
064: PoolingProfile poolingProfile) {
065: this .objectFactory = objectFactory;
066: this .poolingProfile = poolingProfile;
067: }
068:
069: public LifecycleTransitionResult initialise()
070: throws InitialisationException {
071: GenericObjectPool.Config config = new GenericObjectPool.Config();
072:
073: if (poolingProfile != null) {
074: config.maxIdle = poolingProfile.getMaxIdle();
075: config.maxActive = poolingProfile.getMaxActive();
076: config.maxWait = poolingProfile.getMaxWait();
077: config.whenExhaustedAction = (byte) poolingProfile
078: .getExhaustedAction();
079: }
080:
081: pool = new GenericObjectPool(getPooledObjectFactory(), config);
082:
083: try {
084: applyInitialisationPolicy();
085: } catch (Exception e) {
086: throw new InitialisationException(e, this );
087: }
088:
089: return LifecycleTransitionResult.OK;
090: }
091:
092: /**
093: * Template method to be overridden by implementations that do more than just
094: * invoke objectFactory
095: *
096: * @return
097: */
098: protected PoolableObjectFactory getPooledObjectFactory() {
099: return new PoolabeObjectFactoryAdaptor();
100: }
101:
102: protected void applyInitialisationPolicy() throws Exception {
103: if (poolingProfile != null) {
104: int numToBorrow = 0;
105: int initPolicy = poolingProfile.getInitialisationPolicy();
106:
107: if (initPolicy == PoolingProfile.INITIALISE_ALL) {
108: numToBorrow = poolingProfile.getMaxActive();
109: } else if (initPolicy == PoolingProfile.INITIALISE_ONE) {
110: numToBorrow = 1;
111: }
112:
113: List holderList = new ArrayList(numToBorrow);
114: try {
115: for (int t = 0; t < numToBorrow; t++) {
116: holderList.add(objectFactory.getInstance());
117: }
118: } finally {
119: for (int t = 0; t < holderList.size(); t++) {
120: Object obj = holderList.get(t);
121: if (obj != null) {
122: this .returnObject(obj);
123: }
124: }
125: }
126: }
127: }
128:
129: public Object borrowObject() throws Exception {
130: if (pool != null) {
131: return pool.borrowObject();
132: } else {
133: throw new InitialisationException(
134: MessageFactory
135: .createStaticMessage("Object pool has not been initialized."),
136: this );
137: }
138: }
139:
140: public void returnObject(Object object) {
141: if (pool != null) {
142: try {
143: pool.returnObject(object);
144: } catch (Exception ex) {
145: // declared Exception is never thrown from pool; this is a known bug
146: // in
147: // the pool API
148: }
149: }
150: }
151:
152: public int getNumActive() {
153: return pool.getNumActive();
154: }
155:
156: public int getMaxActive() {
157: return pool.getMaxActive();
158: }
159:
160: public void dispose() {
161: if (pool != null) {
162: try {
163: pool.close();
164: } catch (Exception e) {
165: // close() never throws - wrong method signature
166: } finally {
167: pool = null;
168: }
169: }
170: }
171:
172: public void clear() {
173: if (pool != null) {
174: pool.clear();
175: }
176:
177: }
178:
179: public void close() {
180: if (pool != null) {
181: try {
182: pool.close();
183: } catch (Exception e) {
184: // close() never throws - wrong method signature
185: } finally {
186: pool = null;
187: }
188: }
189:
190: }
191:
192: public void setObjectFactory(ObjectFactory objectFactory) {
193: this .objectFactory = objectFactory;
194: }
195:
196: public ObjectFactory getObjectFactory() {
197: return objectFactory;
198: }
199:
200: /**
201: * Wraps org.mule.object.ObjectFactory with commons-pool PoolableObjectFactory
202: */
203: class PoolabeObjectFactoryAdaptor implements PoolableObjectFactory {
204:
205: public void activateObject(Object obj) throws Exception {
206: // nothing to do
207: }
208:
209: public void destroyObject(Object obj) throws Exception {
210: if (obj instanceof Disposable) {
211: ((Disposable) obj).dispose();
212: }
213: }
214:
215: public Object makeObject() throws Exception {
216: return objectFactory.getInstance();
217: }
218:
219: public void passivateObject(Object obj) throws Exception {
220: // nothing to do
221: }
222:
223: public boolean validateObject(Object obj) {
224: return true;
225: }
226:
227: }
228:
229: }
|