001: /*
002: * Copyright 2002-2007 the original author or authors.
003: *
004: * Licensed under the Apache License, Version 2.0 (the "License");
005: * you may not use this file except in compliance with the License.
006: * You may obtain a copy of the License at
007: *
008: * http://www.apache.org/licenses/LICENSE-2.0
009: *
010: * Unless required by applicable law or agreed to in writing, software
011: * distributed under the License is distributed on an "AS IS" BASIS,
012: * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013: * See the License for the specific language governing permissions and
014: * limitations under the License.
015: */
016:
017: package org.springframework.aop.target;
018:
019: import org.springframework.aop.support.DefaultIntroductionAdvisor;
020: import org.springframework.aop.support.DelegatingIntroductionInterceptor;
021: import org.springframework.beans.BeansException;
022: import org.springframework.beans.factory.BeanFactory;
023: import org.springframework.beans.factory.BeanInitializationException;
024: import org.springframework.beans.factory.DisposableBean;
025:
026: /**
027: * Abstract base class for pooling {@link org.springframework.aop.TargetSource}
028: * implementations which maintain a pool of target instances, acquiring and
029: * releasing a target object from the pool for each method invocation.
030: * This abstract base class is independent of concrete pooling technology;
031: * see the subclass {@link CommonsPoolTargetSource} for a concrete example.
032: *
033: * <p>Subclasses must implement the {@link #getTarget} and
034: * {@link #releaseTarget} methods based on their chosen object pool.
035: * The {@link #newPrototypeInstance()} method inherited from
036: * {@link AbstractPrototypeBasedTargetSource} can be used to create objects
037: * in order to put them into the pool.
038: *
039: * <p>Subclasses must also implement some of the monitoring methods from the
040: * {@link PoolingConfig} interface. The {@link #getPoolingConfigMixin()} method
041: * makes these stats available on proxied objects through an IntroductionAdvisor.
042: *
043: * <p>This class implements the {@link org.springframework.beans.factory.DisposableBean}
044: * interface in order to force subclasses to implement a {@link #destroy()}
045: * method, closing down their object pool.
046: *
047: * @author Rod Johnson
048: * @author Juergen Hoeller
049: * @see #getTarget
050: * @see #releaseTarget
051: * @see #destroy
052: */
053: public abstract class AbstractPoolingTargetSource extends
054: AbstractPrototypeBasedTargetSource implements PoolingConfig,
055: DisposableBean {
056:
057: /** The maximum size of the pool */
058: private int maxSize = -1;
059:
060: /**
061: * Set the maximum size of the pool.
062: * Default is -1, indicating no size limit.
063: */
064: public void setMaxSize(int maxSize) {
065: this .maxSize = maxSize;
066: }
067:
068: /**
069: * Return the maximum size of the pool.
070: */
071: public int getMaxSize() {
072: return this .maxSize;
073: }
074:
075: public final void setBeanFactory(BeanFactory beanFactory)
076: throws BeansException {
077: super .setBeanFactory(beanFactory);
078: try {
079: createPool();
080: } catch (Throwable ex) {
081: throw new BeanInitializationException(
082: "Could not create instance pool for TargetSource",
083: ex);
084: }
085: }
086:
087: /**
088: * Create the pool.
089: * @throws Exception to avoid placing constraints on pooling APIs
090: */
091: protected abstract void createPool() throws Exception;
092:
093: /**
094: * Acquire an object from the pool.
095: * @return an object from the pool
096: * @throws Exception we may need to deal with checked exceptions from pool
097: * APIs, so we're forgiving with our exception signature
098: */
099: public abstract Object getTarget() throws Exception;
100:
101: /**
102: * Return the given object to the pool.
103: * @param target object that must have been acquired from the pool
104: * via a call to <code>getTarget()</code>
105: * @throws Exception to allow pooling APIs to throw exception
106: * @see #getTarget
107: */
108: public abstract void releaseTarget(Object target) throws Exception;
109:
110: /**
111: * Return an IntroductionAdvisor that providing a mixin
112: * exposing statistics about the pool maintained by this object.
113: */
114: public DefaultIntroductionAdvisor getPoolingConfigMixin() {
115: DelegatingIntroductionInterceptor dii = new DelegatingIntroductionInterceptor(
116: this );
117: return new DefaultIntroductionAdvisor(dii, PoolingConfig.class);
118: }
119:
120: }
|