2011-04-11 75 views
5

我們有一個應用程序泄漏了一點內存,有點輕描淡寫。Apache Tomcat申請主題

我使用jvisualvm,試圖找到是什麼原因造成的問題。

我看到的線程數成長了不少上啓動名爲線程:HTTP-8080-例如:http:8080-42

我的第一個猜測是,每一個這些線程的是一個請求命中來自客戶端,因爲每個客戶端請求都在其自己的線程中處理。

我的我的問題是,這些線程已運行的時間(迄今10分鐘)長時間。

我的問題是這樣的:

是我的假設是正確的? 如果是這樣,爲什麼線程運行這麼長時間?當然,它仍然無法滿足客戶的要求?

+0

這些線程可能是會話線程嗎? – Koekiebox 2011-04-11 14:25:32

回答

6

的Tomcat總是有許多等待HTTP線程,例如,如果我們看一下默認連接器設置:

<Connector port="80" maxHttpHeaderSize="8192" 
       maxThreads="150" minSpareThreads="25" maxSpareThreads="75" 
       enableLookups="false" redirectPort="8443" acceptCount="100" 
       connectionTimeout="20000" disableUploadTimeout="true" /> 

我們可以看到,至少應該有至少25個線程住,而是在等待連接(達到maxThreads限制)。這由min和maxSpareThreads屬性控制。

什麼JVisual VM狀態的線程正在進行等待或鎖定在資源等等等等?

+0

所有這些線程都處於WAITING狀態:「http-8080-24」 - 線程t @ 70 java.lang.Thread.State:WAITING \t at java.lang.Object.wait(Native Method) \t - 等待<96c084>(一org.apache.tomcat.util.net.JIoEndpoint $工人) \t在java.lang.Object.wait(Object.java:485) \t在org.apache.tomcat.util.net.JIoEndpoint $ Worker.await(JIoEndpoint.java:414) \t at org.apache.tomcat.util.net.JIoEndpoint $ Worker.run(JIoEndpoint.java:440) \t at java.lang.Thread.run(Thread.java :619) 鎖定的擁有同步器: \t - None – Koekiebox 2011-04-11 14:40:37

+0

是的,他們只是在等待更多的連接 - 完美的預期(和理想的行爲)。 :) – Mikaveli 2011-04-11 14:42:21

1

一般來說,應用服務器會預先創建多個線程。應用程序服務器不僅會創建它們,還會保持線程。這被稱爲線程池。服務器將接收一個請求並將其分派給一個線程,並且當該請求完成時,服務器將向該線程分派一個新的請求。

線程創建開銷相當昂貴,因此處理許多請求會從共享線程中受益匪淺。要回答你的問題,調度由服務器創建的線程(假設沒有發生嚴重的運行時錯誤)將在服務器的整個生命週期內運行。

至於你所看到的,如果你看到正在啓動許多許多線程,那麼應用程序的其他部分可以分叉線程這是一個完全獨立的問題。

其重要的是知道你的tomcat服務器不應該爲每個請求創建新線程(再次一般來說)應該重用線程。

2

檢查tomcat連接器配置。請注意0​​和其他線程池的配置。一個常見的錯誤是僅僅增加maxThreads而實際上沒有「調整」。如果你配置一個不必要的大池,它將導致大量的空閒線程。這不會有好處。

儘管很明顯,只是爲了記錄,TIMED_WAITING線程將超時,並且WAITING線程只會爲notify()notifyAll()放置。