Druid como Componente JDBC
Druid es un potente componente JDBC desarrollado por Alibaba. A menudo se le conoce como un pool de conexiones de bases de datos, pero su alcance es mayor. Su arquitectura se basa en un conjunto de componentes integrados:
- DruidDataSource: Un pool de conexiones eficiente y administrable que supera en rendimiento y extensibilidad a soluciones como DBCP, C3P0 o BoneCP.
- DruidDriver: Un driver JDBC proxy que soporta un sistema de plugins basado en el patrón Filter-Chain.
- SQLParser: Un analizador sintáctico para consultas SQL.
Funcionalidades Principales
Druid no solo gestiona conexiones, sino que ofrece herramientas integrales para el monitoreo y la seguridad:
- Monitoreo de Rendimiento SQL: Incluye el plugin StatFilter, el cual recopila estadísticas detalladas sobre la ejecución de consultas, facilitando el análisis en producción.
- Cifrado de Contraseñas: Evita almacenar contraseñas en texto plano en archivos de configuración, apoyando mecanismos seguros mediante callbacks.
- Registro de Actividad (Logging): Proporciona filtros de log compatibles con Common-Logging, Log4j y JDK Logging para registrar cada acceso a la base de datos.
- Extensibilidad: Su sistema de filtros permite a los desarrolladores crear plugins personalizados para itnerceptar y modificar el comportamiento a nivel de JDBC.
Configuración Básica con Spring
Para integrar Druid en una aplicación Spring, se define un bean del tipo DruidDataSource. A continuación, un ejemplo de configuración con parámetros típicos:
<!-- Definición del datasource usando Druid -->
<bean id="fuenteDeDatos" class="com.alibaba.druid.pool.DruidDataSource" destroy-method="close">
<!-- Propiedades de conexión -->
<property name="jdbcUrl" value="${base.datos.url}" />
<property name="username" value="${base.datos.usuario}" />
<property name="password" value="${base.datos.clave}" />
<!-- Habilitar filtro de estadísticas -->
<property name="filters" value="stat" />
<!-- Parámetros del pool -->
<property name="maxActive" value="25" />
<property name="initialSize" value="2" />
<property name="minIdle" value="2" />
<property name="maxWait" value="60000" />
<!-- Limpieza de conexiones inactivas -->
<property name="timeBetweenEvictionRunsMillis" value="60000" />
<property name="minEvictableIdleTimeMillis" value="300000" />
<!-- Validación de conexiones -->
<property name="validationQuery" value="SELECT 1" />
<property name="testWhileIdle" value="true" />
<property name="testOnBorrow" value="false" />
<property name="testOnReturn" value="false" />
<!-- Caché de sentencias preparadas -->
<property name="poolPreparedStatements" value="true" />
<property name="maxPoolPreparedStatementPerConnectionSize" value="20" />
</bean>
Habilitando el Panel de Monitoreo
Druid incluye un panel web para visualizar métricas. Para exponerlo, se debe registrar un servlet en el descriptor de la aplicación (web.xml):
<servlet>
<servlet-name>druidMonitoring</servlet-name>
<servlet-class>com.alibaba.druid.support.http.StatViewServlet</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>druidMonitoring</servlet-name>
<url-pattern>/admin/druid/*</url-pattern>
</servlet-mapping>
Una vez desplegada la aplicación, el panel se puede acceder típicamente en la ruta /admin/druid/index.html.
Monitoreo de Aplicaciones Web
Para correlacionar las solicitudes HTTP con el acceso a la base de datos, se configura un filtro en web.xml:
<filter>
<filter-name>webDataSourceMonitor</filter-name>
<filter-class>com.alibaba.druid.support.http.WebStatFilter</filter-class>
<init-param>
<param-name>exclusions</param-name>
<param-value>*.css,*.js,*.img,/admin/druid/*</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>webDataSourceMonitor</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
Integración con el Monitoreo de Spring
Para obtener métricas de los beans de servicios y DAO de Spring, se puede configurar un interceptor AOP:
<!-- Interceptor de Druid para Spring -->
<bean id="druidSpringInterceptor" class="com.alibaba.druid.support.spring.stat.DruidStatInterceptor"/>
<!-- Punto de corte para capas de servicio y persistencia -->
<bean id="puntoDeCorteDruid" class="org.springframework.aop.support.JdkRegexpMethodPointcut" scope="prototype">
<property name="patterns">
<list>
<value>com.miempresa.servicio.*</value>
<value>com.miempresa.dao.*</value>
</list>
</property>
</bean>
<!-- Configuración del proxy AOP -->
<aop:config proxy-target-class="true">
<aop:advisor advice-ref="druidSpringInterceptor" pointcut-ref="puntoDeCorteDruid"/>
</aop:config>