我们有一个泄漏了一点内存的应用程序,有点轻描淡写。
我正在使用jvisualvm
尝试查找导致问题的原因。
我看到线程数量在以名称开头的线程上增长了很多: http-8080-例如:http:8080-42
我的第一个猜测是,每个线程都是来自客户端的请求命中,因为每个客户端请求都是在自己的线程中处理的。
我的问题是那些线程已经运行了很长一段时间(到目前为止10分钟)。
我的问题是:
我的假设是否正确? 如果是这样,为什么线程运行这么长时间?当然,它仍然无法满足客户的要求吗?
答案 0 :(得分: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声明线程正在等待或锁定资源等等什么?
答案 1 :(得分:2)
检查tomcat连接器配置。注意maxThreads
和其他线程池配置。一个常见的错误就是只增加maxThreads
而不实际“调整”。如果配置不必要的大型池,则会导致大量空闲线程。这没有用。
即使很明显,仅仅是为了记录,TIMED_WAITING线程会超时,而WAITING线程只会出现notify()
或notifyAll()
。
答案 2 :(得分:1)
一般来说,应用程序服务器会预先创建许多线程。应用服务器不仅会创建它们,还会保留线程。这称为线程池。服务器将接收请求并将其分派给线程,当该请求完成时,服务器将向该线程分派新请求。
线程创建开销相当昂贵,因此处理许多请求会从共享线程中获益很多。要回答您的问题,调度服务器创建的线程(假设没有发生严重的运行时错误)将在服务器的生命周期内生效。
至于你所看到的,如果你看到许多线程被启动,那么应用程序的其他部分可能会分叉线程,这是一个完全独立的问题。
重要的是要知道你的tomcat服务器不应该为每个请求创建新线程(一般来说)它应该重用线程。