c3p0 中的资源无法检出的原因?

Reasons why resources in c3p0 cannot get checked out?

所以我正在研究 c3p0 API 以调试我们的生产问题之一,该问题导致在检查连接时出现堆栈溢出错误。

我在 BasicResourcePool class 的 checkoutResource 方法中找到以下评论:

    /*
 * This function recursively calls itself... under nonpathological
 * situations, it shouldn't be a problem, but if resources can never
 * successfully check out for some reason, we might blow the stack...
 *
 * by the semantics of wait(), a timeout of zero means forever.
 */

我想知道此池中的资源永远无法成功检出的可能原因。

答案可能会帮助我了解我的申请中可能出现的问题。

因此,虽然这是一个合理的猜测,但单纯的池耗尽(如果泄漏或忘记关闭()连接会发生什么)不会导致堆栈溢出。

checkoutResource(...)

时发生栈溢出
  1. 找到一个可以签出的连接,"preliminarily"将其签出;然后
  2. 出问题了,说明初步签出的Connection不可用;所以
  3. 函数运行 "back to the well",递归调用自身以使用新的连接重试

谜底在"something goes wrong"部分。确实有两件事可能出错:

  1. (最有可能!)您已将 testConnectionOnCheckout 设置为 true,并且所有连接都未通过其连接测试
  2. 在结帐过程中,连接碰巧从池中删除(例如超过 maxIdleTimemaxConnectionAge 已过期)

如果您看到这个,首先要检查您的连接或连接测试机制是否有问题。尝试...

  1. DEBUGFINE 处记录 com.mchange.v2.resourcepool.BasicResourcePool 并查找指示无法结帐的异常。您可以 grep for A resource could not be refurbished for checkout. 或者,switch Connection testing regimes 测试空闲连接和连接签入而不是签出,并以一种可能不那么破坏性的方式观察问题的出现。
  2. 如果您正在做一些会迫使池真正搅动连接的事情,设置非常短的超时或其他东西,可以想象竞争条件正在发生。检查 configuration properties maxConnectionAgemaxIdleTimemaxIdleTimeExcessConnections 的值并确保它们设置合理或未设置(即保持合理的默认值)。