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 * https://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.PrintWriter; 020import java.time.Duration; 021import java.time.Instant; 022import java.util.Deque; 023 024/** 025 * Defines the wrapper that is used to track the additional information, such as 026 * state, for the pooled objects. 027 * <p> 028 * Implementations of this class are required to be thread-safe. 029 * </p> 030 * 031 * @param <T> the type of object in the pool. 032 * @since 2.0 033 */ 034public interface PooledObject<T> extends Comparable<PooledObject<T>> { 035 036 /** 037 * Gets the wrapped object or null. 038 * 039 * @param <T> the type of object in the pool. 040 * @param pooledObject the PooledObject to unwrap, may be null. 041 * @return the wrapped object or null. 042 * @since 2.13.0 043 */ 044 static <T> T getObject(final PooledObject<T> pooledObject) { 045 return pooledObject != null ? pooledObject.getObject() : null; 046 } 047 048 /** 049 * Tests whether the given PooledObject is null <em>or</em> wraps a null. 050 * 051 * @param pooledObject the PooledObject to test, may be null. 052 * @return whether the given PooledObject is null <em>or</em> wraps a null. 053 * @since 2.12.0 054 */ 055 static boolean isNull(final PooledObject<?> pooledObject) { 056 return getObject(pooledObject) == null; 057 } 058 059 /** 060 * Tests whether the given PooledObject isn't null <em>and</em> doesn't wraps a null. 061 * 062 * @param pooledObject the PooledObject to test, may be null. 063 * @return whether the given PooledObject isn't null <em>and</em> doesn't wraps a null. 064 * @since 2.13.0 065 */ 066 static boolean nonNull(final PooledObject<?> pooledObject) { 067 return getObject(pooledObject) != null; 068 } 069 070 /** 071 * Allocates the object. 072 * 073 * @return {@code true} if the original state was {@link PooledObjectState#IDLE IDLE} 074 */ 075 boolean allocate(); 076 077 /** 078 * Orders instances based on idle time - i.e. the length of time since the 079 * instance was returned to the pool. Used by the GKOP idle object evictor. 080 * <p> 081 * Note: This class has a natural ordering that is inconsistent with 082 * equals if distinct objects have the same identity hash code. 083 * </p> 084 * <p> 085 * {@inheritDoc} 086 * </p> 087 */ 088 @Override 089 int compareTo(PooledObject<T> other); 090 091 /** 092 * Deallocates the object and sets it {@link PooledObjectState#IDLE IDLE} 093 * if it is currently {@link PooledObjectState#ALLOCATED ALLOCATED}. 094 * 095 * @return {@code true} if the state was {@link PooledObjectState#ALLOCATED ALLOCATED}. 096 */ 097 boolean deallocate(); 098 099 /** 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}