JavaApache意外暂停以发出请求
运行web应用程序一天后,登录加载正常,但不起作用。日志显示tomcat在请求时暂停
我正在使用:
- 春天3
- c3p0
- MySql
- 和Tomcat 7
日志如下:
Jan 06, 2014 9:56:18 PM org.apache.coyote.AbstractProtocol pause
INFO: Pausing ProtocolHandler ["http-bio-8080"]
Jan 06, 2014 9:56:18 PM org.apache.coyote.AbstractProtocol pause
INFO: Pausing ProtocolHandler ["ajp-bio-8009"]
Jan 06, 2014 9:56:18 PM org.apache.catalina.core.StandardService stopInternal
INFO: Stopping service Catalina
Jan 06, 2014 9:56:18 PM org.apache.catalina.core.StandardWrapper unload
INFO: Waiting for 19 instance(s) to be deallocated for Servlet [Faces Servlet]
Jan 06, 2014 9:56:19 PM org.apache.catalina.core.StandardWrapper unload
INFO: Waiting for 19 instance(s) to be deallocated for Servlet [Faces Servlet]
Jan 06, 2014 9:56:20 PM org.apache.catalina.core.StandardWrapper unload
INFO: Waiting for 19 instance(s) to be deallocated for Servlet [Faces Servlet]
Jan 06, 2014 9:56:20 PM org.apache.catalina.core.StandardWrapper unload
INFO: Waiting for 18 instance(s) to be deallocated for Servlet [default]
Jan 06, 2014 9:56:21 PM org.apache.catalina.core.StandardWrapper unload
INFO: Waiting for 18 instance(s) to be deallocated for Servlet [default]
Jan 06, 2014 9:56:22 PM org.apache.catalina.core.StandardWrapper unload
INFO: Waiting for 18 instance(s) to be deallocated for Servlet [default]
java.sql.SQLException: An SQLException was provoked by the following failure: java.lang.InterruptedException
at com.mchange.v2.sql.SqlUtils.toSQLException(SqlUtils.java:106)
at com.mchange.v2.sql.SqlUtils.toSQLException(SqlUtils.java:65)
at com.mchange.v2.sql.SqlUtils.toSQLException(SqlUtils.java:62)
at com.mchange.v2.c3p0.impl.C3P0PooledConnectionPool.checkoutPooledConnection(C3P0PooledConnectionPool.java:531)
at com.mchange.v2.c3p0.impl.AbstractPoolBackedDataSource.getConnection(AbstractPoolBackedDataSource.java:128)
at com.tda.financiero.common.JasperReportProvider.llenarReporte(JasperReportProvider.java:116)
at com.tda.financiero.common.JasperReportProvider.ejecutarReportePDF(JasperReportProvider.java:53)
at com.tda.financiero.common.ReporteServiceImpl.generarFacturaPDF(ReporteServiceImpl.java:26)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:606)
at org.springframework.aop.support.AopUtils.invokeJoinpointUsingReflection(AopUtils.java:318)
at org.springframework.aop.framework.ReflectiveMethodInvocation.invokeJoinpoint(ReflectiveMethodInvocation.java:183)
...
Caused by: java.lang.InterruptedException
at java.lang.Object.wait(Native Method)
at com.mchange.v2.resourcepool.BasicResourcePool.awaitAvailable(BasicResourcePool.java:1315)
at com.mchange.v2.resourcepool.BasicResourcePool.prelimCheckoutResource(BasicResourcePool.java:557)
at com.mchange.v2.resourcepool.BasicResourcePool.checkoutResource(BasicResourcePool.java:477)
at com.mchange.v2.c3p0.impl.C3P0PooledConnectionPool.checkoutPooledConnection(C3P0PooledConnectionPool.java:525)
... 79 more
Jan 06, 2014 9:56:22 PM javax.faces.event.MethodExpressionActionListener processAction
SEVERE: Received 'java.lang.NullPointerException' when invoking action listener '#{userManagedBean.login()}' for component 'login'
Jan 06, 2014 9:56:23 PM javax.faces.event.MethodExpressionActionListener processAction
SEVERE: java.lang.NullPointerException
at org.apache.catalina.session.ManagerBase.generateSessionId(ManagerBase.java:807)
at org.apache.catalina.session.ManagerBase.createSession(ManagerBase.java:653)
该日志还显示一个NullPointerException,但位于另一个异常之后。有什么想法吗?如果你能给我一些提示,告诉我该去哪里看,或者如何着手分析这个问题,那就太好了。谢谢
编辑
我使用Spring的applicationContext文件配置c3p0池连接,所有DAO都使用sessionFactory,服务用@Transactional注释。简言之,弹簧控制连接。只有2个用户使用这个应用程序,我认为使用c3p0默认值就足够了,所以我有了这个配置
<bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource" destroy-method="close">
<property name="driverClass" value="${jdbc.driver}"/>
<property name="jdbcUrl" value="${jdbc.url}"/>
<property name="user" value="${jdbc.username}"/>
<property name="password" value="${jdbc.password}"/>
<property name="testConnectionOnCheckin" value="true"/>
<property name="idleConnectionTestPeriod" value="3600"/>
<property name="preferredTestQuery" value="SELECT 1" />
</bean>
<!-- Session Factory Declaration -->
<bean id="sessionFactory" class="org.springframework.orm.hibernate4.LocalSessionFactoryBean">
<property name="dataSource" ref="dataSource" />
<property name="packagesToScan" value="com.tda.financiero.domain.model"/>
<property name="hibernateProperties">
<props>
<prop key="hibernate.dialect">org.hibernate.dialect.MySQLDialect</prop>
<!-- <prop key="hibernate.show_sql">true</prop> -->
</props>
</property>
</bean>
<!-- Enable the configuration of transactional behavior based on annotations -->
<tx:annotation-driven transaction-manager="txManager"/>
<!-- Transaction Manager is defined -->
<bean id="txManager" class="org.springframework.orm.hibernate4.HibernateTransactionManager">
<property name="sessionFactory" ref="sessionFactory"/>
</bean>
# 1 楼答案
因此,您有一些客户端试图从c3p0数据源签出连接,但等待()因为没有可用的连接。在某种程度上,这些线程是中断()ed。不可能通过中断()ed的内容来说明上面列出的内容。这些线程看起来并不是显式超时的[c3p0有一个名为
checkoutTimeout
的配置参数,因为那样的话,您会看到一个TimeoutException
而不是InterruptedException
所以,有一件事值得怀疑,是什么打断了这些线索?它们是客户端线程,可能是Tomcat产生的,而不是c3p0内部线程。c3p0没有打断他们
另一个可能更高效的问题是,为什么这些线程要等待连接池中本应该对它们可用的连接?您的连接池对于它所经历的负载是否太小,在这种情况下,最好的响应是增加c3p0参数
maxPoolSize
?连接池的负载是否太大,以至于尽管有足够大的maxPoolSize
,连接维护任务仍会积压?在这种情况下,c3p0配置属性numHelperThreads
可能会有所帮助或者,可能是最常见的问题,应用程序是否泄漏连接?也就是说,它是否偶尔从数据源签出连接,但最终无法
close()
?即使在清理finally块中的其他资源时发生异常,您的应用程序是否确保它签出的所有连接都在finally块中关闭?如果运行Java7,您是否会使用全新的try with resources语法获取连接您没有提供有关应用程序的规模、负载或配置的任何信息,但连接泄漏是导致线程在尝试获取数据库连接时挂起时间过长的最常见原因。c3p0有两个配置参数unreturnedConnectionTimeout和debugUnreturnedConnectionStackTraces,可帮助您解决问题和(请!)调试并修复连接泄漏。见讨论here
根据您提供的信息,使用这些参数检查是否存在参数泄漏是我尝试的第一件事
但是,如果你知道你的应用程序有很高的并发负载,你可以使用
maxPoolSize
。通过JMX,您可以监视c3p0的线程池是否正常运行,或者是否希望增加numHelperThreads