Java 使用带有tomcat的c3p0与MySQL的僵尸连接

Java 使用带有tomcat的c3p0与MySQL的僵尸连接,java,mysql,tomcat,connection-pooling,c3p0,Java,Mysql,Tomcat,Connection Pooling,C3p0,我正在使用c3p0来管理到MySQL的数据库连接。 问题是有些连接被永久保留。我有1000个连接的限制,但由于未知原因,有1200个打开的连接。为了研究它,我在tomcat服务器外壳中执行以下命令: netstat-n | grep3306 | grep已建立| wc-l 它返回1200 以下是context.xml <Resource name="jdbc/xxxx" auth="Container" user="xxxxxx" password

我正在使用c3p0来管理到MySQL的数据库连接。 问题是有些连接被永久保留。我有1000个连接的限制,但由于未知原因,有1200个打开的连接。为了研究它,我在tomcat服务器外壳中执行以下命令:

netstat-n | grep3306 | grep已建立| wc-l

它返回1200

以下是
context.xml

 <Resource name="jdbc/xxxx" auth="Container"
          user="xxxxxx"
          password="xxxxx"
          driverClass="com.mysql.jdbc.Driver"
          jdbcUrl ="jdbc:mysql://xxxx:3306/xxx"
          factory="org.apache.naming.factory.BeanFactory"
          type="com.mchange.v2.c3p0.ComboPooledDataSource"
          maxPoolSize="1000"
          minPoolSize="200"
          numHelperThreads="10"
          acquireIncrement="50"
          maxStatementsPerConnection="0"
          idleConnectionTestPeriod="200"
          maxIdleTime = "1000"
          maxIdleTimeExcessConnections = "180"
          maxStatements="200"
          unreturnedConnectionTimeout="10"
          debugUnreturnedConnectionStackTraces="true"
          />

OBS:我没有在这个应用程序中使用hibernate(只是在几个类中)。大多数连接都是通过纯JDBC代码进行的。

有几种可能性

最可能的情况是,您已将此资源元素放置在
$CATALINA_BASE/conf/context.xml
文件中,该文件为每个web应用程序提供默认的context.xml。因此,如果您有六个web应用程序,那么您将有六个连接池。由于最小轮询大小为200,因此将至少打开200*6=1200个数据库连接

另一种可能是web应用程序已重新加载。您应该获得一个新的连接池,旧的连接池将被GC'd。但是,如果在重新加载时发生内存泄漏(很容易做到,不需要意识到),它可能会将连接池及其打开的连接保留在内存中,从而增加总连接数

要将定义放入
server.xml
,请执行以下操作:

<Server>
  <GlobalNamingResources>
     <Resource name="jdbc/xxxx">...</Resource>
  </GlobalNamingResources>
</Server>
  <ResourceLink name="jdbc/xxxx"
      global="jdbc/xxxx"
      type="com.mchange.v2.c3p0.ComboPooledDataSource" />

有两种可能性

最可能的情况是,您已将此资源元素放置在
$CATALINA_BASE/conf/context.xml
文件中,该文件为每个web应用程序提供默认的context.xml。因此,如果您有六个web应用程序,那么您将有六个连接池。由于最小轮询大小为200,因此将至少打开200*6=1200个数据库连接

另一种可能是web应用程序已重新加载。您应该获得一个新的连接池,旧的连接池将被GC'd。但是,如果在重新加载时发生内存泄漏(很容易做到,不需要意识到),它可能会将连接池及其打开的连接保留在内存中,从而增加总连接数

要将定义放入
server.xml
,请执行以下操作:

<Server>
  <GlobalNamingResources>
     <Resource name="jdbc/xxxx">...</Resource>
  </GlobalNamingResources>
</Server>
  <ResourceLink name="jdbc/xxxx"
      global="jdbc/xxxx"
      type="com.mchange.v2.c3p0.ComboPooledDataSource" />

我将资源放在server.xml中,但无法通过应用程序访问它。如何操作?server.xml中定义的资源是资源,需要通过RsourceLink链接到单个上下文。在将逻辑移动到server.xml后,我仍然存在连接数大于池中最大连接数的情况。我认为,出于某种原因,游泳池有一个漏洞。。。有什么想法吗?似乎不太可能,但可能。切换到Tomcat的内置连接池是确定c3p0是否有bug的一种方法。我想我发现了这个BUG:我的网站有很多访问权限。当我在tomcat启动时将tomcat机器置于负载平衡时,问题就出现了。在这一刻,我认为出于某种竞争条件的原因,当c3p0在构建连接池的同时收到大量请求时,c3p0会失去对其自身连接的控制。只是一个猜测,但当我在tomcat启动后等待几秒钟将其放入负载平衡时,问题不再出现。我将资源放在server.xml中,但无法通过应用程序访问它。如何操作?server.xml中定义的资源是资源,需要通过RsourceLink链接到单个上下文。在将逻辑移动到server.xml后,我仍然存在连接数大于池中最大连接数的情况。我认为,出于某种原因,游泳池有一个漏洞。。。有什么想法吗?似乎不太可能,但可能。切换到Tomcat的内置连接池是确定c3p0是否有bug的一种方法。我想我发现了这个BUG:我的网站有很多访问权限。当我在tomcat启动时将tomcat机器置于负载平衡时,问题就出现了。在这一刻,我认为出于某种竞争条件的原因,当c3p0在构建连接池的同时收到大量请求时,c3p0会失去对其自身连接的控制。只是一个猜测,但当我在tomcat启动后等待几秒钟将其放入负载平衡时,问题就不再出现了