    001/*
    002 * Licensed to the Apache Software Foundation (ASF) under one or more
    003 * contributor license agreements.  See the NOTICE file distributed with
    004 * this work for additional information regarding copyright ownership.
    005 * The ASF licenses this file to You under the Apache License, Version 2.0
    006 * (the "License"); you may not use this file except in compliance with
    007 * the License.  You may obtain a copy of the License at
    008 *
    009 *      http://www.apache.org/licenses/LICENSE-2.0
    010 *
    011 * Unless required by applicable law or agreed to in writing, software
    012 * distributed under the License is distributed on an "AS IS" BASIS,
    013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    014 * See the License for the specific language governing permissions and
    015 * limitations under the License.
    016 */
    017package org.apache.commons.pool2;
    018
    019import java.io.Closeable;
    020import java.util.NoSuchElementException;
    021
    022/**
    023 * A "keyed" pooling interface.
    024 * <p>
    025 * A keyed pool maintains a pool of instances for each key value.
    026 * </p>
    027 * <p>
    028 * Example of use:
    029 * </p>
    030 * <pre style="border:solid thin; padding: 1ex;"
    031 * > Object obj = <code style="color:#00C">null</code>;
    032 * Object key = <code style="color:#C00">"Key"</code>;
    033 *
    034 * <code style="color:#00C">try</code> {
    035 *     obj = pool.borrowObject(key);
    036 *     <code style="color:#0C0">//...use the object...</code>
    037 * } <code style="color:#00C">catch</code>(Exception e) {
    038 *     <code style="color:#0C0">// invalidate the object</code>
    039 *     pool.invalidateObject(key, obj);
    040 *     <code style="color:#0C0">// do not return the object to the pool twice</code>
    041 *     obj = <code style="color:#00C">null</code>;
    042 * } <code style="color:#00C">finally</code> {
    043 *     <code style="color:#0C0">// make sure the object is returned to the pool</code>
    044 *     <code style="color:#00C">if</code>(<code style="color:#00C">null</code> != obj) {
    045 *         pool.returnObject(key, obj);
    046 *     }
    047 * }</pre>
    048 * <p>
    049 * {@link KeyedObjectPool} implementations <i>may</i> choose to store at most
    050 * one instance per key value, or may choose to maintain a pool of instances
    051 * for each key (essentially creating a {@link java.util.Map Map} of
    052 * {@link ObjectPool pools}).
    053 * </p>
    054 * <p>
    055 * See {@link org.apache.commons.pool2.impl.GenericKeyedObjectPool
    056 * GenericKeyedObjectPool} for an implementation.
    057 * </p>
    058 *
    059 * @param <K> The type of keys maintained by this pool.
    060 * @param <V> Type of element pooled in this pool.
    061 *
    062 * @see KeyedPooledObjectFactory
    063 * @see ObjectPool
    064 * @see org.apache.commons.pool2.impl.GenericKeyedObjectPool GenericKeyedObjectPool
    065 *
    066 * @since 2.0
    067 */
    068public interface KeyedObjectPool<K, V> extends Closeable {
    069    /**
    070     * Obtains an instance from this pool for the specified <code>key</code>.
    071     * <p>
    072     * Instances returned from this method will have been either newly created
    073     * with {@link KeyedPooledObjectFactory#makeObject makeObject} or will be
    074     * a previously idle object and have been activated with
    075     * {@link KeyedPooledObjectFactory#activateObject activateObject} and then
    076     * (optionally) validated with
    077     * {@link KeyedPooledObjectFactory#validateObject validateObject}.
    078     * </p>
    079     * <p>
    080     * By contract, clients <strong>must</strong> return the borrowed object
    081     * using {@link #returnObject returnObject},
    082     * {@link #invalidateObject invalidateObject}, or a related method as
    083     * defined in an implementation or sub-interface, using a <code>key</code>
    084     * that is {@link Object#equals equivalent} to the one used to borrow the
    085     * instance in the first place.
    086     * </p>
    087     * <p>
    088     * The behaviour of this method when the pool has been exhausted is not
    089     * strictly specified (although it may be specified by implementations).
    090     * </p>
    091     *
    092     * @param key the key used to obtain the object
    093     *
    094     * @return an instance from this pool.
    095     *
    096     * @throws IllegalStateException
    097     *              after {@link #close close} has been called on this pool
    098     * @throws Exception
    099     *              when {@link KeyedPooledObjectFactory#makeObject
    100     *              makeObject} throws an exception
    101     * @throws NoSuchElementException
    102     *              when the pool is exhausted and cannot or will not return
    103     *              another instance
    104     */
    105    V borrowObject(K key) throws Exception, NoSuchElementException, IllegalStateException;
    106
    107    /**
    108     * Return an instance to the pool. By contract, <code>obj</code>
    109     * <strong>must</strong> have been obtained using
    110     * {@link #borrowObject borrowObject} or a related method as defined in an
    111     * implementation or sub-interface using a <code>key</code> that is
    112     * equivalent to the one used to borrow the instance in the first place.
    113     *
    114     * @param key the key used to obtain the object
    115     * @param obj a {@link #borrowObject borrowed} instance to be returned.
    116     *
    117     * @throws IllegalStateException
    118     *              if an attempt is made to return an object to the pool that
    119     *              is in any state other than allocated (i.e. borrowed).
    120     *              Attempting to return an object more than once or attempting
    121     *              to return an object that was never borrowed from the pool
    122     *              will trigger this exception.
    123     *
    124     * @throws Exception if an instance cannot be returned to the pool
    125     */
    126    void returnObject(K key, V obj) throws Exception;
    127
    128    /**
    129     * Invalidates an object from the pool.
    130     * <p>
    131     * By contract, <code>obj</code> <strong>must</strong> have been obtained
    132     * using {@link #borrowObject borrowObject} or a related method as defined
    133     * in an implementation or sub-interface using a <code>key</code> that is
    134     * equivalent to the one used to borrow the <code>Object</code> in the first
    135     * place.
    136     * </p>
    137     * <p>
    138     * This method should be used when an object that has been borrowed is
    139     * determined (due to an exception or other problem) to be invalid.
    140     * </p>
    141     *
    142     * @param key the key used to obtain the object
    143     * @param obj a {@link #borrowObject borrowed} instance to be returned.
    144     *
    145     * @throws Exception if the instance cannot be invalidated
    146     */
    147    void invalidateObject(K key, V obj) throws Exception;
    148
    149    /**
    150     * Create an object using the {@link KeyedPooledObjectFactory factory} or
    151     * other implementation dependent mechanism, passivate it, and then place it
    152     * in the idle object pool. <code>addObject</code> is useful for
    153     * "pre-loading" a pool with idle objects (Optional operation).
    154     *
    155     * @param key the key a new instance should be added to
    156     *
    157     * @throws Exception
    158     *              when {@link KeyedPooledObjectFactory#makeObject} fails.
    159     * @throws IllegalStateException
    160     *              after {@link #close} has been called on this pool.
    161     * @throws UnsupportedOperationException
    162     *              when this pool cannot add new idle objects.
    163     */
    164    void addObject(K key) throws Exception, IllegalStateException,
    165            UnsupportedOperationException;
    166
    167    /**
    168     * Returns the number of instances corresponding to the given
    169     * <code>key</code> currently idle in this pool. Returns a negative value if
    170     * this information is not available.
    171     *
    172     * @param key the key to query
    173     * @return the number of instances corresponding to the given
    174     * <code>key</code> currently idle in this pool.
    175     */
    176    int getNumIdle(K key);
    177
    178    /**
    179     * Returns the number of instances currently borrowed from but not yet
    180     * returned to the pool corresponding to the given <code>key</code>.
    181     * Returns a negative value if this information is not available.
    182     *
    183     * @param key the key to query
    184     * @return the number of instances currently borrowed from but not yet
    185     * returned to the pool corresponding to the given <code>key</code>.
    186=     */
    187    int getNumActive(K key);
    188
    189    /**
    190     * Returns the total number of instances currently idle in this pool.
    191     * Returns a negative value if this information is not available.
    192     * @return the total number of instances currently idle in this pool.
    193 =    */
    194    int getNumIdle();
    195
    196    /**
    197     * Returns the total number of instances currently borrowed from this pool but
    198     * not yet returned. Returns a negative value if this information is not
    199     * available.
    200     * @return the total number of instances currently borrowed from this pool but
    201     * not yet returned.
    202     */
    203    int getNumActive();
    204
    205    /**
    206     * Clears the pool, removing all pooled instances (optional operation).
    207     *
    208     * @throws UnsupportedOperationException when this implementation doesn't
    209     *                                       support the operation
    210     *
    211     * @throws Exception if the pool cannot be cleared
    212     */
    213    void clear() throws Exception, UnsupportedOperationException;
    214
    215    /**
    216     * Clears the specified pool, removing all pooled instances corresponding to
    217     * the given <code>key</code> (optional operation).
    218     *
    219     * @param key the key to clear
    220     *
    221     * @throws UnsupportedOperationException when this implementation doesn't
    222     *                                       support the operation
    223     *
    224     * @throws Exception if the key cannot be cleared
    225     */
    226    void clear(K key) throws Exception, UnsupportedOperationException;
    227
    228    /**
    229     * Close this pool, and free any resources associated with it.
    230     * <p>
    231     * Calling {@link #addObject addObject} or
    232     * {@link #borrowObject borrowObject} after invoking this method on a pool
    233     * will cause them to throw an {@link IllegalStateException}.
    234     * </p>
    235     * <p>
    236     * Implementations should silently fail if not all resources can be freed.
    237     * </p>
    238     */
    239    @Override
    240    void close();
    241}