Tomcat会忽略removeAbandonedTimeout并关闭池中的连接

时间:2018-10-24 17:34:21

标签: tomcat jdbc ibm-midrange connection-pool dbcp

我正在使用tomcat 7.0,通过使用Commons dbcp的as400上的DB2进行JDBC连接。一旦在服务器上加了负载,它就会立即打开和关闭与数据库的连接,而忽略了我设置的30分钟的removeAbandonedTimeout设置。我尝试了几种设置都无济于事。例如,在15秒的间隔内,它将打开150个连接并关闭140,而没有明显的原因。我们已经在旧的WebSphere服务器上运行了该应用程序,除非它们真正处于空闲状态,否则它不会关闭连接。

这是我的配置:

 <Resource name="MYDB"
          auth="Container"
          type="javax.sql.DataSource"
          factory="org.apache.tomcat.dbcp.dbcp.BasicDataSourceFactory"
          driverClassName="com.ibm.as400.access.AS400JDBCDriver"
          url="jdbc:as400://mydb.na.sysco.net;blockCriteria=2;dateFormat=iso;libraries=*LIBL;naming=system;errors=full"
          username="user"
          password="pass"
          maxActive="350"
          maxWait="180000"
          minIdle="10"
          maxIdle="50"
          testWhileIdle="true"
          validationQuery="select 1 from sysibm.sysdummy1"
          timeBetweenEvictionRunsMillis="34000"
          minEvictableIdleTimeMillis="1800000"
          removeAbandonedTimeout="1800"
          removeAbandoned="true"
          logAbandoned="true"/>

当系统处于空闲状态或只有几个测试帐户时,它会按预期运行,但是一旦我在服务器上加了负载,就会立即开始大量的打开和关闭。例如,它将在相同的15秒间隔内打开150个连接并关闭90个连接。我正在从我的监控软件中读取与as400上QZ作业的开始和结束相关的套接字打开和关闭。使用连接时,它将连续执行此操作。

这违反了连接池的目的。任何想法都可以得到赞赏。

也令人困惑,因为不清楚应该使用哪个参数作为开始。 Tomcat JDBC连接池参数中唯一的公共dbcp参数不被接受,即removeAbandonedOnMaintenance。但是会从Tomcat jdbc池参数中获取minEvictableIdleTimeMillis的默认值1800000,而不是60000。

https://commons.apache.org/proper/commons-dbcp/api-1.2.2/index.html

https://tomcat.apache.org/tomcat-7.0-doc/jdbc-pool.html

当我没有明确设置参数时,这就是默认值。它似乎列出了所有tomcat jdbc池参数,而不列出commons DBCP参数。但是,它将从公共DBCP中选择minEvictableIdleTimeout的默认值,而不是从Tomcat JDBC连接池参数中选择60秒的默认值。奇怪的部分是公用dbcp的removeAbandoned参数未列出,它是removeAbandonedOnMaintenance和removeAbandonedOnBorrow。我一直在努力将这种果冻钉在墙上一个星期。

我使用jmxproxy来获取实时统计信息和设置。

http://myserver:8080/manager/jmxproxy/?qry=Catalina%3Atype%3DDataSource%2C *

Name: Catalina:type=DataSource,class=javax.sql.DataSource,name="EOPDB"
modelerType: org.apache.tomcat.util.modeler.BaseModelMBean
maxIdle: 8
testOnBorrow: false
defaultTransactionIsolation: -1
testOnReturn: false
maxActive: 350
numActive: 104
numTestsPerEvictionRun: 3
minIdle: 0
maxWait: 180000
closed: false
defaultAutoCommit: true
numIdle: 8
validationQueryTimeout: -1    
testWhileIdle: false
driverClassName: com.ibm.as400.access.AS400JDBCDriver
accessToUnderlyingConnectionAllowed: false
url: jdbc:as400://mydb;blockCriteria=2;dateFormat=iso;libraries=*LIBL;naming=system;errors=full
removeAbandonedTimeout: 300
defaultReadOnly: false
logAbandoned: false
poolPreparedStatements: false
maxOpenPreparedStatements: -1
removeAbandoned: false
minEvictableIdleTimeMillis: 1800000
timeBetweenEvictionRunsMillis: -1
initialSize: 0

2 个答案:

答案 0 :(得分:0)

在您的情况下,有2个值可能会出现问题

      timeBetweenEvictionRunsMillis="34000"
      removeAbandoned="true"

timeBetweenEvictionRunsMillis
这是34秒,在您的场景中,在该时间段的中间创建了150个连接,当时间到了90个销毁了,在池中留下了60个连接,几乎是maxIdle = 50请求的50个连接。与 minEvictableIdleTimeMillis 相比,它看起来不成比例,因为您希望空闲连接在池中保持30分钟(1800000 ms)的状态,但是每34秒检查一次却不采取任何措施,因为连接的寿命应该更长。

removeAbandonedTimeout 这迫使您的应用程序以1.8秒的速度运行查询。

  

该值应设置为您的应用程序可能具有的最长运行查询。

确保您的应用程序正确地将连接返回到池,它们将被视为已放弃并关闭。
希望这会有所帮助。

选项为explained here

答案 1 :(得分:0)

maxIdle是池中可以保持空闲状态的最大连接数。一旦空闲连接数超过maxIdle,应用程序释放的任何连接将立即关闭,而无需根据minEvictableIdleTimeMillis检查连接空闲时间。