2011-04-18 8 views
9

Estoy utilizando la agrupación de conexiones dbcp en tomcat (versión 7) y tengo una pérdida de conexión en algún lugar de mi código. Después de un corto período de tiempo, una solicitud para una nueva conexión devuelve la siguiente excepción:Intentando identificar el origen de las conexiones abandonadas en tomcat

"No se puede obtener una conexión, error de la piscina Tiempo de espera para el objeto inactivo"

Volví a través de mi código y para mí parece que todas las conexiones se cierran correctamente (no todos dicen esto ...).

Con el fin de depurar este he añadido las siguientes propiedades en context.xml:

logAbandoned="true" removeAbandoned="true" removeAbandonedTimeout="300" 

Así que el código de recurso ahora se ve así: Tomcat

<Resource name="jdbc/findata" auth="Container" type="javax.sql.DataSource" 
       maxActive="20" maxIdle="5" maxWait="10000" 
       username="root" password="xxxxxx" driverClassName="com.mysql.jdbc.Driver" 
       logAbandoned="true" removeAbandoned="true" removeAbandonedTimeout="300" 
       url="jdbc:mysql://localhost:3306/findata"/> 

entonces me reinicia y comenzó a golpear Web páginas hasta que apareció el mensaje de error (en la ventana del navegador). Sin embargo, todavía no he podido averiguar dónde está escribiendo la información de la propiedad "logAbandoned". Estoy mirando en

/usr/share/apache-tomcat-7.0.11/logs 

pero el archivo de registro sólo recientemente modificado en La Haya

localhost_access_log.2011-04-18.txt 

Cualquier ayuda es muy apreciada.

+0

Nunca terminé averiguando cómo conseguir que las conexiones abandonadas aparezcan en los registros, pero volví a revisar el código en otra ocasión y esta vez tuve éxito en descifrar la fuente de la fuga. ¿Quién necesita depuradores o registros? ¿Verdad? ;) – opike

Respuesta

4

Lo que hice en un escenario similar fue guardar subprocesos de subprocesos que solicitan conexiones, y luego en otro subproceso imprimir subprocesos de hilo correspondientes a cada conexión abierta en cada minuto más o menos. Supongo que esta es la forma de fuerza bruta de hacerlo. Pero resolví mi problema bastante rápido.

+1

Bueno uno. Y eliminar la pila del mapa en close(), ¿verdad? Simple y eficiente. –

3

Una forma relativamente fácil de asegurarse de cerrar siempre una conexión es colocarla en el filtro de servlet, colocarla en ThreadLocal, usar ThreadLocal en todo su código y cerrarla cuando la respuesta regrese al filtro. (Una optimización sería colocar un proxy en ThreadLocal que obtiene conexión en la primera solicitud solamente).

Pero su problema inmediato es encontrar la fuente de la fuga, ¿verdad?

Primero, asegúrese de cerrar las conexiones en la sentencia finally {}, por lo que una excepción no le impedirá hacerlo.

En segundo lugar, no está claro cuánto tiempo le lleva a logAbandoned descubrir que la conexión está inactiva. Intente esperar un tiempo, pueden ser 15 minutos más o menos.

En tercer lugar, puede usar controladores proxy JDBC como http://code.google.com/p/log4jdbc/. Generan un registro de todas las actividades a través de las conexiones, por lo que puede grep el registro para encontrar desajuste abrir() y cerrar().

¡Buena suerte!

7

Según this site debe proporcionar una fábrica a su definición de recurso de su context.xml. La configuración del recurso se realizará con esta instancia de fábrica, por lo que todos los parámetros "adicionales" se configuran de esta manera. Para ser más específico, tendría algo como esto en su context.xml (o servidor).xml - depende donde se define su recurso):

<Resource name="jdbc/db" auth="Container" type="javax.sql.DataSource" 
factory="org.apache.tomcat.jdbc.pool.DataSourceFactory" 
driverClassName="org.postgresql.Driver" url="jdbc:postgresql://127.0.0.1/db" 
username="hibernate" password="hibernate" maxActive="20" maxIdle="10" 
maxWait="1000" removeAbandoned="true" removeAbandonedTimeout="20" 
logAbandoned="true" /> 

Aviso factory="org.apache.tomcat.jdbc.pool.DataSourceFactory" la cual es esencial para nuestro propósito. Sin él, el removeAbandoned="true" no tiene ningún efecto.

Las pilas de cada conexión que se abandona se almacenan en catalina.log ($tomcat_dir/logs). A partir de allí dará detalles bastante precisos para las conexiones de depuración.

Aparte de los parámetros "abandonados" puede configurar muchas cosas en relación con el rendimiento del conjunto jdbc de tomcat, los tiempos de espera y otros matices y pernos. Por supuesto, esto requiere un profundo conocimiento. (Puede encontrar detalles en el sitio que proporcioné inicialmente)

+0

¿Dónde encontraste la información que la fábrica es esencial para eliminar Abandonado? No tengo una fábrica en mi configuración local. Sin embargo, las conexiones abandonadas se están cerrando. – KoenigGunther

+0

Esto se indica como se requiere en la documentación de tomcat 7 https://tomcat.apache.org/tomcat-7.0-doc/jdbc-pool.html –

Cuestiones relacionadas