2011-09-18 41 views
1

我们最近开始看到我们的tomcat服务器的线程数量出现峰值(峰值通常在100左右时超过1000)。我们在其中一个tomcat服务器上执行了线程转储,同时它的线程数很高,并且发现大量线程正在等待MultiThreadedHttpConnectionManager $ ConnectionPool,堆栈跟踪如下:由等待线程导致的高线程数tomcat线程池MultiThreadedHttpConnectionManager ConnectionPool

“TP-Processor21700”守护进程prio = 10 TID = 0x4a0b3400 NID = 0x2091中的Object.wait()[0x399f3000..0x399f4004] java.lang.Thread.State中:WAITING(对象监视器上) 在java.lang.Object.wait(本机方法) - 等待在< 0x58ee5030>(a org.apache.commons.httpclient.MultiThreadedHttpConnectionManager $ ConnectionPool) at org.apache.commons.httpclient.MultiThreadedHttpConnectionManager.doGetConnection(MultiThreadedHttpConnectionManager.java:518) - locked < 0x58ee5030>(一个org.apache.commons.httpclient.MultiThreadedHttpConnectionManager $连接池) 在org.apache.commons.httpclient.MultiThreadedHttpConnectionManager.getConnectionWithTimeout(MultiThreadedHttpConnectionManager.java:416) 在org.apache.commons.httpclient.HttpMethodDirector.executeMethod (HttpMethodDirector.java:153) 在org.apache.commons.httpclient.HttpClient.executeMethod(HttpClient.java:397) 在org.apache.commons.httpclient.HttpClient.executeMethod(HttpClient.java:323) ..

在我们的代码中有3个点,其中调用了httpClient.executeMethod()(通过对另一个tomcat服务器的http请求获取信息)。在每种情况下,传递给它的GetMethod对象的套接字超时值都已设置(即通过getMethod.getParams()。setSoTimeout();),而MultiThreadedConnectionManager在spring中配置为具有10秒的connectionTimeout值。我注意到的一件事是,3个httpClient.executeMethod()调用中只有2个调用getMethod.releaseConnection(),所以我想知道这是否可能是问题的原因(即连接不明确发布)。然而奇怪的是,这个问题只是在最近几天才开始发生的,并且源代码在一年内还没有被修改,再加上最近没有通过tomcat服务器的请求激增。在问题发生之前几天发生的一个变化是,我们将tomcat服务器使用的JVM从Java 5(1.5更新14)升级到Java 6(1.6更新25)。我们已经尝试了暂时将JVM版本恢复到Java 5,以查看问题是否停止发生,但没有发生。另一点需要注意的是,在大多数情况下,tomcat服务器最终会恢复并且线程数会恢复正常 - 我们只有一个tomcat进程由于线程数增加而崩溃的实例。

我们正在运行Tomcat 5.5,使用commons-httpclient-3.1.jar在Red Hat Linux环境中针对Java 1.6更新25运行。

请让我知道,如果你能提出任何想法,可能是这个问题的原因。

谢谢。

回答

2

问题确实是由于3个httpClient.executeMethod(getMethod)调用中只有2个调用getMethod.releaseConnection()后引起的。确保所有3个httpClient.executeMethod(getMethod)调用位于try/catch块内,后跟一个包含对getMethod.releaseConnection()的调用的finally块,以防止发生高线程计数。虽然这段代码在我们的实时系统中已经使用了一年多,但似乎最近才开始出现高线程数问题的原因是因为各种搜索引擎爬虫已经开始用大量的URL请求来触发该网站,导致代码在连接正在使用中,但随后不会执行。问题解决了。