オブジェクトプールのGenericObjectPool構成パラメーターの詳細な説明

オブジェクトプールのGenericObjectPool構成パラメーターの詳細な説明

頼る

    <dependency>
        <groupId>org.apache.commons</groupId>
        <artifactId>commons-pool2</artifactId>
        <version>2.4.3</version>
    </dependency>

使用するにはGenericObjectPoolを、学ぶことが必要であるGenericObjectPoolConfig。設定パラメータは、以下に説明します。

1.親クラスBaseObjectPoolConfig構成パラメーター

/**
 * Provides the implementation for the common attributes shared by the
 * sub-classes. New instances of this class will be created using the defaults
 * defined by the public constants.
 * <p>
 * This class is not thread-safe.
 *  * @since 2.0
 */
public abstract class BaseObjectPoolConfig extends BaseObject implements Cloneable {
    private boolean lifo = DEFAULT_LIFO;

    private boolean fairness = DEFAULT_FAIRNESS;

    private long maxWaitMillis = DEFAULT_MAX_WAIT_MILLIS;

    private long minEvictableIdleTimeMillis = DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS;

    private long evictorShutdownTimeoutMillis = DEFAULT_EVICTOR_SHUTDOWN_TIMEOUT_MILLIS;

    private long softMinEvictableIdleTimeMillis = DEFAULT_SOFT_MIN_EVICTABLE_IDLE_TIME_MILLIS;

    private int numTestsPerEvictionRun = DEFAULT_NUM_TESTS_PER_EVICTION_RUN;

    private String evictionPolicyClassName = DEFAULT_EVICTION_POLICY_CLASS_NAME;

    private boolean testOnCreate = DEFAULT_TEST_ON_CREATE;

    private boolean testOnBorrow = DEFAULT_TEST_ON_BORROW;

    private boolean testOnReturn = DEFAULT_TEST_ON_RETURN;

    private boolean testWhileIdle = DEFAULT_TEST_WHILE_IDLE;

    private long timeBetweenEvictionRunsMillis = DEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS;

    private boolean blockWhenExhausted = DEFAULT_BLOCK_WHEN_EXHAUSTED;

    private boolean jmxEnabled = DEFAULT_JMX_ENABLE;

    private String jmxNamePrefix = DEFAULT_JMX_NAME_PREFIX;

    private String jmxNameBase = DEFAULT_JMX_NAME_BASE;
}
  • lifo

    、後入れ先出し(LIFO)と先入れ先出し(FIFO)の2つの動作モードをプールに提供します。デフォルトのDEFAULT_LIFO = true、プールで使用可能な空きオブジェクトがある場合、borrowObjectメソッドを呼び出すと最新のものが返されます(後入れ先出し)インスタンス。
    org.apache.commons.pool2.impl.GenericObjectPool

        if (getLifo()) {
            idleObjects.addFirst(p);
        } else {
            idleObjects.addLast(p);
        }
  • 公平性
    プールからリソースを取得するときに使用するか、プールにリソースを返すときに使用するか。java.util.concurrent.locks.ReentrantLock.ReentrantLockの公平性ロックメカニズム。
    デフォルトDEFAULT_FAIRNESS = false
    org.apache.commons.pool2.impl.GenericObjectPool

    idleObjects = new LinkedBlockingDeque<PooledObject<T>>(config.getFairness());
  • maxWaitMillis
    接続プールのリソースが使い果たされると、呼び出し元が接続を取得するまでの最大待機時間(単位:ミリ秒)。
    デフォルト値はDEFAULT_MAX_WAIT_MILLIS = -1Lであり、タイムアウトすることはありません。
    org.apache.commons.pool2.impl.GenericObjectPool

    @Override
    public T borrowObject() throws Exception {
        return borrowObject(getMaxWaitMillis());
    }
  • minEvictableIdleTimeMillis
    は、接続の最小アイドル時間です。この値に達すると、アイドル接続が削除される場合があります(アイドル接続の最大数に達したかどうかによって異なり
    ます)。デフォルト値DEFAULT_MIN_EVICTABLE_IDLE_TIME_MILLIS = 1000L 60L 30L
    org.apache.commons .pool2.impl.GenericObjectPool

    final EvictionConfig evictionConfig = new EvictionConfig(
                        getMinEvictableIdleTimeMillis(),
                        getSoftMinEvictableIdleTimeMillis(),
                        getMinIdle());
  • evictorShutdownTimeoutMillis
    は、エビクションスレッドのタイムアウト時間を閉じます。
    デフォルト値DEFAULT_EVICTOR_SHUTDOWN_TIMEOUT_MILLIS = 10L * 1000L
    org.apache.commons.pool2.impl.BaseGenericObjectPool

    final void startEvictor(final long delay) {
        synchronized (evictionLock) {
            if (null != evictor) {
                EvictionTimer.cancel(evictor, evictorShutdownTimeoutMillis, TimeUnit.MILLISECONDS);
                evictor = null;
                evictionIterator = null;
            }
            if (delay > 0) {
                evictor = new Evictor();
                EvictionTimer.schedule(evictor, delay, delay);
            }
        }
    }
  • softMinEvictableIdleTimeMillis
    は、接続がアイドル状態である最小時間です。この値に達すると、アイドル状態のリンクが削除され、minIdleのアイドル状態の接続が保持されます。
    デフォルト値はDEFAULT_SOFT_MIN_EVICTABLE_IDLE_TIME_MILLIS = -1です。

  • numTestsPerEvictionRun
    は、アイドルオブジェクトスレッドが実行されるたびに検出されたアイドルオブジェクトの数を検出します
    。numTestsPerEvictionRun> = 0の場合、numTestsPerEvictionRunの小さい方の値とプール内の接続数が、毎回検出される接続数として使用されます
    。numTestsPerEvictionRun<の場合0、毎回チェックされる接続数は、プール内の接続の総数をこの値の絶対値で除算して切り上げた結果です。
    デフォルト値DEFAULT_NUM_TESTS_PER_EVICTION_RUN = 3
    org.apache.commons.pool2.impl.GenericObjectPool

        private int getNumTests() {
            final int numTestsPerEvictionRun = getNumTestsPerEvictionRun();
            if (numTestsPerEvictionRun >= 0) {
                return Math.min(numTestsPerEvictionRun, idleObjects.size());
            }
            return (int) (Math.ceil(idleObjects.size() /
                    Math.abs((double) numTestsPerEvictionRun)));
        }
  • evictionPolicyClassNameエビクション
    ポリシーのクラス名。
    デフォルト値DEFAULT_EVICTION_POLICY_CLASS_NAME = "org.apache.commons.pool2.impl.DefaultEvictionPolicy"
    org.apache.commons.pool2.impl.GenericObjectPool

       public final void setEvictionPolicyClassName(final String evictionPolicyClassName) {
            try {
                Class<?> clazz;
                try {
                    clazz = Class.forName(evictionPolicyClassName, true, Thread.currentThread().getContextClassLoader());
                } catch (final ClassNotFoundException e) {
                    clazz = Class.forName(evictionPolicyClassName);
                }
                final Object policy = clazz.newInstance();
                if (policy instanceof EvictionPolicy<?>) {
                    @SuppressWarnings("unchecked") // safe, because we just checked the class
                    final EvictionPolicy<T> evicPolicy = (EvictionPolicy<T>) policy;
                    this.evictionPolicy = evicPolicy;
                } else {
                    throw new IllegalArgumentException("[" + evictionPolicyClassName + "] does not implement EvictionPolicy");
                }
            } catch (final ClassNotFoundException e) {
                throw new IllegalArgumentException("Unable to create EvictionPolicy instance of type " + evictionPolicyClassName, e);
            } catch (final InstantiationException e) {
                throw new IllegalArgumentException("Unable to create EvictionPolicy instance of type " + evictionPolicyClassName, e);
            } catch (final IllegalAccessException e) {
                throw new IllegalArgumentException("Unable to create EvictionPolicy instance of type " + evictionPolicyClassName, e);
            }
        }
  • testOnCreate
    は、オブジェクトの作成時にオブジェクトが有効かどうかを検出します(true:yes)。trueを構成するとパフォーマンスが低下します。
    デフォルト値はDEFAULT_TEST_ON_CREATE = falseです。
    org.apache.commons.pool2.impl.GenericObjectPool ## BorrowObject(final long BorrowMaxWaitMillis)

        PooledObject<T> p = null;
        // ...省略
        // 配置true,新创建对象都会检测对象是否有效 【 create && getTestOnCreate() 】
        if (p != null && (getTestOnBorrow() || create && getTestOnCreate())) {
            boolean validate = false;
            Throwable validationThrowable = null;
            try {
                validate = factory.validateObject(p);
            } catch (final Throwable t) {
                PoolUtils.checkRethrow(t);
                validationThrowable = t;
            }
            if (!validate) {
                try {
                    destroy(p);
                    destroyedByBorrowValidationCount.incrementAndGet();
                } catch (final Exception e) {
                    // Ignore - validation failure is more important
                }
                p = null;
                if (create) {
                    final NoSuchElementException nsee = new NoSuchElementException("Unable to validate object");
                    nsee.initCause(validationThrowable);
                    throw nsee;
                }
            }
        }
  • testOnBorrow
    は、オブジェクトプールからオブジェクトを取得するときにオブジェクトが有効かどうかを検出し(true:yes)、trueを構成するとパフォーマンスが低下します。
    デフォルト値DEFAULT_TEST_ON_BORROW = false
    org.apache.commons.pool2.impl.GenericObjectPool ## BorrowObject(final long BorrowMaxWaitMillis)**
    // 配置true,从对象池获取对象,总是要检测对象是否有效 【 getTestOnBorrow() 】
    if (p != null && (getTestOnBorrow() || create && getTestOnCreate())) {
        // ...省略
    }
  • testOnReturn
    は、オブジェクトをオブジェクトプールに返すときにオブジェクトが有効かどうかを検出します(true:yes)。trueに設定するとパフォーマンスが低下します。
    デフォルト値DEFAULT_TEST_ON_RETURN = false
    org.apache.commons.pool2.impl.GenericObjectPool ## returnObject (最終的なT obj)

        if (getTestOnReturn()) {
            if (!factory.validateObject(p)) {
                try {
                    destroy(p);
                } catch (final Exception e) {
                    swallowException(e);
                }
                try {
                    ensureIdle(1, false);
                } catch (final Exception e) {
                    swallowException(e);
                }
                updateStatsReturn(activeTime);
                return;
            }
        }

  • アイドル状態のオブジェクトを検出するスレッドがオブジェクトを削除する必要がないことを検出したときに、testWhileIdleがオブジェクトの有効性を検出するかどうかtrueに設定することをお勧めします。これは、パフォーマンスに影響を与えず、安全性を確保し
    ますデフォルト値DEFAULT_TEST_WHILE_IDLE = false
    org.apache.commons.pool2.impl.GenericObjectPool ## evict()

        final boolean testWhileIdle = getTestWhileIdle();
        // .... 代码省略
        // 配置为true, 检测空闲对象线程检测到对象不需要移除时,检测对象的有效性
        if (testWhileIdle) {
            boolean active = false;
            try {
                factory.activateObject(underTest);
                active = true;
            } catch (final Exception e) {
                destroy(underTest);
                destroyedByEvictorCount.incrementAndGet();
            }
            if (active) {
                if (!factory.validateObject(underTest)) {
                    destroy(underTest);
                    destroyedByEvictorCount.incrementAndGet();
                } else {
                    try {
                        factory.passivateObject(underTest);
                    } catch (final Exception e) {
                        destroy(underTest);
                        destroyedByEvictorCount.incrementAndGet();
                    }
                }
            }
        }
  • timeBetweenEvictionRunsMillis
    アイドル接続検出サイクル(ミリ秒単位)。負の値の場合、検出スレッドが実行されていないことを意味します。
    デフォルト値はDEFAULT_TIME_BETWEEN_EVICTION_RUNS_MILLIS = -1Lorg.apache.commons.pool2.impl.GenericObjectPool
    です。

        public GenericObjectPool(final PooledObjectFactory<T> factory, final GenericObjectPoolConfig config) {
            super(config, ONAME_BASE, config.getJmxNamePrefix());
            if (factory == null) {
                jmxUnregister(); // tidy up
                throw new IllegalArgumentException("factory may not be null");
            }
            this.factory = factory;
    
            idleObjects = new LinkedBlockingDeque<PooledObject<T>>(config.getFairness());
    
            setConfig(config);
            // 启动空闲连接检测线程
            startEvictor(getTimeBetweenEvictionRunsMillis());
        }
  • blockWhenExhausted
    オブジェクトプールに空きオブジェクトがない場合、オブジェクトを取得するための新しいリクエストがブロックされるかどうか(trueブロッキング、maxWaitMillisが有効になります。接続プールにリソースがなく、すぐに例外をスローする場合はfalse)
    デフォルト値DEFAULT_BLOCK_WHEN_EXHAUSTED = true
    org.apache.commons.pool2.impl.GenericObjectPool ## BorrowObject(final long BorrowMaxWaitMillis)

        final boolean blockWhenExhausted = getBlockWhenExhausted();
        // ... 省略
        if (blockWhenExhausted) {
            if (p == null) {
                if (borrowMaxWaitMillis < 0) {
                    p = idleObjects.takeFirst();
                } else {
                    p = idleObjects.pollFirst(borrowMaxWaitMillis,
                            TimeUnit.MILLISECONDS);
                }
            }
            if (p == null) {
                throw new NoSuchElementException(
                        "Timeout waiting for idle object");
            }
        } 
  • jmxEnabled
    がJMXに登録されているかどうか
    デフォルトDEFAULT_JMX_ENABLE = true
    org.apache.commons.pool2.impl.BaseGenericObjectPool

        public BaseGenericObjectPool(final BaseObjectPoolConfig config, final String jmxNameBase, final String jmxNamePrefix) {
            if (config.getJmxEnabled()) {
                this.oname = jmxRegister(config, jmxNameBase, jmxNamePrefix);
            } else {
                this.oname = null;
            }
    
            // Populate the creation stack trace
            this.creationStackTrace = getStackTrace(new Exception());
    
            // save the current TCCL (if any) to be used later by the evictor Thread
            final ClassLoader cl = Thread.currentThread().getContextClassLoader();
            if (cl == null) {
                factoryClassLoader = null;
            } else {
                factoryClassLoader = new WeakReference<ClassLoader>(cl);
            }
    
            fairness = config.getFairness();
        }
  • jmxNamePrefixJMX
    プレフィックスの
    デフォルト値DEFAULT_JMX_NAME_PREFIX = "pool"
    org.apache.commons.pool2.impl.GenericObjectPool

        // JMX specific attributes
        private static final String ONAME_BASE = "org.apache.commons.pool2:type=GenericObjectPool,name=";
    
        public GenericObjectPool(final PooledObjectFactory<T> factory, final GenericObjectPoolConfig config) {
            // 参见上述 jmxEnabled 部分
            super(config, ONAME_BASE, config.getJmxNamePrefix());
            // .....
        }
  • jmxNameBase
    はbase + jmxNamePrefix + iを使用してObjectNameの
    デフォルト値DEFAULT_JMX_NAME_BASE = nullを生成しGenericObjectPool構築メソッドはONAME_BASE初期化を使用します。

        private ObjectName jmxRegister(final BaseObjectPoolConfig config,final String jmxNameBase, String jmxNamePrefix) {
            ObjectName objectName = null;
            final MBeanServer mbs = ManagementFactory.getPlatformMBeanServer();
            int i = 1;
            boolean registered = false;
            String base = config.getJmxNameBase();
            if (base == null) {
                base = jmxNameBase;
            }
            while (!registered) {
                try {
                    ObjectName objName;
                    if (i == 1) {
                        objName = new ObjectName(base + jmxNamePrefix);
                    } else {
                        objName = new ObjectName(base + jmxNamePrefix + i);
                    }
                    mbs.registerMBean(this, objName);
                    objectName = objName;
                    registered = true;
                } catch (final MalformedObjectNameException e) {
                    if (BaseObjectPoolConfig.DEFAULT_JMX_NAME_PREFIX.equals(jmxNamePrefix) && jmxNameBase.equals(base)) {
                        // 如果走到这步,就跳过jmx注册,应该不会发生
                        registered = true;
                    } else {
                        // 前者使用的名称不是默认配置,则使用默认配置替代
                        jmxNamePrefix =
                                BaseObjectPoolConfig.DEFAULT_JMX_NAME_PREFIX;
                        base = jmxNameBase;
                    }
                } catch (final InstanceAlreadyExistsException e) {
                    // 增加一个索引,再试一次
                    i++;
                } catch (final MBeanRegistrationException e) {
                    // 如果走到这步,就跳过jmx注册,应该不会发生
                    registered = true;
                } catch (final NotCompliantMBeanException e) {
                    // 如果走到这步,就跳过jmx注册,应该不会发生
                    registered = true;
                }
            }
            return objectName;
        }
    

2.サブクラスGenericObjectPoolConfig構成パラメーター

/**
 * A simple "struct" encapsulating the configuration for a
 * {@link GenericObjectPool}.
 *  * <p>
 * This class is not thread-safe; it is only intended to be used to provide
 * attributes used when creating a pool.
 *  * @since 2.0
 */
public class GenericObjectPoolConfig extends BaseObjectPoolConfig {

    private int maxTotal = DEFAULT_MAX_TOTAL;

    private int maxIdle = DEFAULT_MAX_IDLE;

    private int minIdle = DEFAULT_MIN_IDLE;
}
  • maxTotal
    最大接続数、デフォルト値DEFAULT_MAX_TOTAL = 8
  • maxIdle
    アイドル接続の最大数、デフォルト値DEFAULT_MAX_IDLE = 8
  • minIdle
    アイドル接続の最小数、デフォルト値DEFAULT_MIN_IDLE = 0

おすすめ

転載: blog.51cto.com/huazie/2676978