View Javadoc
1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one or more
3    * contributor license agreements.  See the NOTICE file distributed with
4    * this work for additional information regarding copyright ownership.
5    * The ASF licenses this file to You under the Apache License, Version 2.0
6    * (the "License"); you may not use this file except in compliance with
7    * the License.  You may obtain a copy of the License at
8    *
9    *      https://www.apache.org/licenses/LICENSE-2.0
10   *
11   * Unless required by applicable law or agreed to in writing, software
12   * distributed under the License is distributed on an "AS IS" BASIS,
13   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14   * See the License for the specific language governing permissions and
15   * limitations under the License.
16   */
17  package org.apache.commons.pool2;
18  
19  import java.io.PrintWriter;
20  import java.time.Duration;
21  import java.time.Instant;
22  import java.util.Deque;
23  
24  /**
25   * Defines the wrapper that is used to track the additional information, such as
26   * state, for the pooled objects.
27   * <p>
28   * Implementations of this class are required to be thread-safe.
29   * </p>
30   *
31   * @param <T> the type of object in the pool.
32   * @since 2.0
33   */
34  public interface PooledObject<T> extends Comparable<PooledObject<T>> {
35  
36      /**
37       * Gets the wrapped object or null.
38       *
39       * @param <T> the type of object in the pool.
40       * @param pooledObject the PooledObject to unwrap, may be null.
41       * @return the wrapped object or null.
42       * @since 2.13.0
43       */
44      static <T> T getObject(final PooledObject<T> pooledObject) {
45          return pooledObject != null ? pooledObject.getObject() : null;
46      }
47  
48      /**
49       * Tests whether the given PooledObject is null <em>or</em> wraps a null.
50       *
51       * @param pooledObject the PooledObject to test, may be null.
52       * @return whether the given PooledObject is null <em>or</em> wraps a null.
53       * @since 2.12.0
54       */
55      static boolean isNull(final PooledObject<?> pooledObject) {
56          return getObject(pooledObject) == null;
57      }
58  
59      /**
60       * Tests whether the given PooledObject isn't null <em>and</em> doesn't wraps a null.
61       *
62       * @param pooledObject the PooledObject to test, may be null.
63       * @return whether the given PooledObject isn't null <em>and</em> doesn't wraps a null.
64       * @since 2.13.0
65       */
66      static boolean nonNull(final PooledObject<?> pooledObject) {
67          return getObject(pooledObject) != null;
68      }
69  
70      /**
71       * Allocates the object.
72       *
73       * @return {@code true} if the original state was {@link PooledObjectState#IDLE IDLE}
74       */
75      boolean allocate();
76  
77      /**
78       * Orders instances based on idle time - i.e. the length of time since the
79       * instance was returned to the pool. Used by the GKOP idle object evictor.
80       * <p>
81       * Note: This class has a natural ordering that is inconsistent with
82       *       equals if distinct objects have the same identity hash code.
83       * </p>
84       * <p>
85       * {@inheritDoc}
86       * </p>
87       */
88      @Override
89      int compareTo(PooledObject<T> other);
90  
91      /**
92       * Deallocates the object and sets it {@link PooledObjectState#IDLE IDLE}
93       * if it is currently {@link PooledObjectState#ALLOCATED ALLOCATED}.
94       *
95       * @return {@code true} if the state was {@link PooledObjectState#ALLOCATED ALLOCATED}.
96       */
97      boolean deallocate();
98  
99      /**
100      * Notifies the object that the eviction test has ended.
101      *
102      * @param idleQueue The queue of idle objects to which the object should be
103      *                  returned.
104      * @return  Currently not used.
105      */
106     boolean endEvictionTest(Deque<PooledObject<T>> idleQueue);
107 
108     @Override
109     boolean equals(Object obj);
110 
111     /**
112      * Gets the amount of time this object last spent in the active state (it may still be active in which case
113      * subsequent calls will return an increased value).
114      *
115      * @return The duration last spent in the active state.
116      * @since 2.11.0
117      */
118     default Duration getActiveDuration() {
119         // Take copies to avoid threading issues
120         final Instant lastReturnInstant = getLastReturnInstant();
121         final Instant lastBorrowInstant = getLastBorrowInstant();
122         // @formatter:off
123         return lastReturnInstant.isAfter(lastBorrowInstant) ?
124                 Duration.between(lastBorrowInstant, lastReturnInstant) :
125                 Duration.between(lastBorrowInstant, Instant.now());
126         // @formatter:on
127     }
128 
129     /**
130      * Gets the amount of time this object last spent in the active state (it may still be active in which case
131      * subsequent calls will return an increased value).
132      *
133      * @return The duration last spent in the active state.
134      * @since 2.10.0
135      * @deprecated Use {@link #getActiveDuration()}.
136      */
137     @Deprecated
138     default Duration getActiveTime() {
139         return getActiveDuration();
140     }
141 
142     /**
143      * Gets the amount of time in milliseconds this object last spent in the
144      * active state (it may still be active in which case subsequent calls will
145      * return an increased value).
146      *
147      * @return The time in milliseconds last spent in the active state.
148      * @deprecated Use {@link #getActiveTime()} which offers the best precision.
149      */
150     @Deprecated
151     long getActiveTimeMillis();
152 
153     /**
154      * Gets the number of times this object has been borrowed.
155      *
156      * @return -1 by default for implementations prior to release 2.7.0.
157      * @since 2.7.0
158      */
159     default long getBorrowedCount() {
160         return -1;
161     }
162 
163     /**
164      * Gets the time (using the same basis as {@link Instant#now()}) that this object was created.
165      *
166      * @return The creation time for the wrapped object.
167      * @since 2.11.0
168      */
169     default Instant getCreateInstant() {
170         return Instant.ofEpochMilli(getCreateTime());
171     }
172 
173     /**
174      * Gets the time (using the same basis as
175      * {@link java.time.Clock#instant()}) that this object was created.
176      *
177      * @return The creation time for the wrapped object.
178      * @deprecated Use {@link #getCreateInstant()} which offers the best precision.
179      */
180     @Deprecated
181     long getCreateTime();
182 
183     /**
184      * Gets the duration since this object was created (using {@link Instant#now()}).
185      *
186      * @return The duration since this object was created.
187      * @since 2.12.0
188      */
189     default Duration getFullDuration() {
190         return Duration.between(getCreateInstant(), Instant.now());
191     }
192 
193     /**
194      * Gets the amount of time that this object last spend in the
195      * idle state (it may still be idle in which case subsequent calls will
196      * return an increased value).
197      *
198      * @return The amount of time in last spent in the idle state.
199      * @since 2.11.0
200      */
201     default Duration getIdleDuration() {
202         return Duration.ofMillis(getIdleTimeMillis());
203     }
204 
205     /**
206      * Gets the amount of time that this object last spend in the
207      * idle state (it may still be idle in which case subsequent calls will
208      * return an increased value).
209      *
210      * @return The amount of time in last spent in the idle state.
211      * @since 2.10.0
212      * @deprecated Use {@link #getIdleDuration()}.
213      */
214     @Deprecated
215     default Duration getIdleTime() {
216         return Duration.ofMillis(getIdleTimeMillis());
217     }
218 
219     /**
220      * Gets the amount of time in milliseconds that this object last spend in the
221      * idle state (it may still be idle in which case subsequent calls will
222      * return an increased value).
223      *
224      * @return The time in milliseconds last spent in the idle state.
225      * @deprecated Use {@link #getIdleTime()} which offers the best precision.
226      */
227     @Deprecated
228     long getIdleTimeMillis();
229 
230     /**
231      * Gets the time the wrapped object was last borrowed.
232      *
233      * @return The time the object was last borrowed.
234      * @since 2.11.0
235      */
236     default Instant getLastBorrowInstant() {
237         return Instant.ofEpochMilli(getLastBorrowTime());
238     }
239 
240     /**
241      * Gets the time the wrapped object was last borrowed.
242      *
243      * @return The time the object was last borrowed.
244      * @deprecated Use {@link #getLastBorrowInstant()} which offers the best precision.
245      */
246     @Deprecated
247     long getLastBorrowTime();
248 
249     /**
250      * Gets the time the wrapped object was last borrowed.
251      *
252      * @return The time the object was last borrowed.
253      * @since 2.11.0
254      */
255     default Instant getLastReturnInstant() {
256         return Instant.ofEpochMilli(getLastReturnTime());
257     }
258 
259     /**
260      * Gets the time the wrapped object was last returned.
261      *
262      * @return The time the object was last returned.
263      * @deprecated Use {@link #getLastReturnInstant()} which offers the best precision.
264      */
265     @Deprecated
266     long getLastReturnTime();
267 
268     /**
269      * Gets an estimate of the last time this object was used. If the class of the pooled object implements
270      * {@link TrackedUse}, what is returned is the maximum of {@link TrackedUse#getLastUsedInstant()} and
271      * {@link #getLastBorrowTime()}; otherwise this method gives the same value as {@link #getLastBorrowTime()}.
272      *
273      * @return the last time this object was used
274      * @since 2.11.0
275      */
276     default Instant getLastUsedInstant() {
277         return Instant.ofEpochMilli(getLastUsedTime());
278     }
279 
280     /**
281      * Gets an estimate of the last time this object was used.  If the class
282      * of the pooled object implements {@link TrackedUse}, what is returned is
283      * the maximum of {@link TrackedUse#getLastUsedInstant()} and
284      * {@link #getLastBorrowTime()}; otherwise this method gives the same
285      * value as {@link #getLastBorrowTime()}.
286      *
287      * @return the last time this object was used.
288      * @deprecated Use {@link #getLastUsedInstant()} which offers the best precision.
289      */
290     @Deprecated
291     long getLastUsedTime();
292 
293     /**
294      * Gets the underlying object that is wrapped by this instance of
295      * {@link PooledObject}.
296      *
297      * @return The wrapped object.
298      */
299     T getObject();
300 
301     /**
302      * Gets the state of this object.
303      *
304      * @return state
305      */
306     PooledObjectState getState();
307 
308     @Override
309     int hashCode();
310 
311     /**
312      * Sets the state to {@link PooledObjectState#INVALID INVALID}.
313      */
314     void invalidate();
315 
316     /**
317      * Marks the pooled object as abandoned.
318      */
319     void markAbandoned();
320 
321     /**
322      * Marks the object as returning to the pool.
323      */
324     void markReturning();
325 
326     /**
327      * Prints the stack trace of the code that borrowed this pooled object and
328      * the stack trace of the last code to use this object (if available) to
329      * the supplied writer.
330      *
331      * @param   writer  The destination for the debug output.
332      */
333     void printStackTrace(PrintWriter writer);
334 
335     /**
336      * Sets whether to use abandoned object tracking. If this is true the
337      * implementation will need to record the stack trace of the last caller to
338      * borrow this object.
339      *
340      * @param   logAbandoned    The new configuration setting for abandoned
341      *                          object tracking.
342      */
343     void setLogAbandoned(boolean logAbandoned);
344 
345     /**
346      * Sets the stack trace generation strategy based on whether or not fully detailed stack traces are required.
347      * When set to false, abandoned logs may only include caller class information rather than method names, line
348      * numbers, and other normal metadata available in a full stack trace.
349      *
350      * @param requireFullStackTrace the new configuration setting for abandoned object logging.
351      * @since 2.7.0
352      */
353     default void setRequireFullStackTrace(final boolean requireFullStackTrace) {
354         // noop
355     }
356 
357     /**
358      * Attempts to place the pooled object in the
359      * {@link PooledObjectState#EVICTION} state.
360      *
361      * @return {@code true} if the object was placed in the
362      *         {@link PooledObjectState#EVICTION} state otherwise
363      *         {@code false}.
364      */
365     boolean startEvictionTest();
366 
367     /**
368      * Gets a String form of the wrapper for debug purposes. The format is
369      * not fixed and may change at any time.
370      *
371      * {@inheritDoc}
372      */
373     @Override
374     String toString();
375 
376     /**
377      * Records the current stack trace as the last time the object was used.
378      */
379     void use();
380 
381 }