Estoy desarrollando un proyecto en el trabajo para el que tengo que crear y mantener tablas de resumen por razones de rendimiento. Creo que el término correcto para esto es Vistas materializadas.Método preferido para vistas materializadas (tablas de resumen) con MySQL
tengo 2 razones principales para hacer esto:
Denormalization
normalicé las mesas tanto como sea posible. Entonces hay situaciones en las que tendría que unirme a muchas tablas para extraer datos. Trabajamos con MySQL Cluster, que tiene un rendimiento bastante pobre cuando se trata de JOIN.
Necesito crear tablas desnormalizadas que puedan ejecutar SELECT más rápido.
resumir los datos
Por ejemplo, tengo una tabla Transacciones con unos pocos millones de registros. Las transacciones provienen de diferentes sitios web. La aplicación necesita generar un informe que muestre los recuentos de transacciones diarias o mensuales y los montos totales de ingresos por sitio web. No quiero que la secuencia de comandos del informe calcule esto cada vez, así que necesito generar una tabla de resumen que tenga un desglose por [sitio, fecha].
Eso es solo un ejemplo simple. Hay muchos tipos diferentes de tablas de resumen que necesito generar y mantener.
En el pasado he hecho estas cosas escribiendo varios scripts cron para mantener cada tabla de resumen actualizada. Pero en este nuevo proyecto, espero implementar una solución más elegante y adecuada.
Preferiría una solución basada en PHP, ya que no soy un administrador del servidor, y me siento más cómodo cuando puedo controlar todo a través de mi código de aplicación.
Soluciones que he considerado:
copia de VISTA
Si la tabla resultante se puede representar como una sola consulta SELECT, puedo generar una vista . Como son lentas, puede haber un cronjob que copie esta VISTA en una tabla real.
Sin embargo, algunas de estas consultas SELECT pueden ser tan lentas que no son aceptables incluso para cronjobs. No es muy eficiente recrear todos los datos de resumen, si las filas anteriores ni siquiera se actualizan mucho.
Cronjobs personalizados para cada Cuadro Resumen
Esta es la solución que he usado antes, pero ahora estoy tratando de evitarla si es posible. Si habrá muchas tablas de resumen, puede ser complicado mantenerlas.
MySQL disparadores
Es posible añadir factores desencadenantes de las tablas principales de modo que cada vez que hay un INSERT, UPDATE o DELETE, las tablas de resumen se actualizan en consecuencia.
No habría cronjobs y los resúmenes serían en tiempo real. Sin embargo, si alguna vez fuera necesario reconstruir una tabla de resumen desde cero, tendría que hacerse con otra solución (probablemente la n. ° 1 anterior).
El uso de ORM Ganchos/disparadores
estoy usando Doctrina como mi ORM. Hay una forma de agregar detectores de eventos que desencadenarán cosas en INSERT/UPDATE/DELETE, que a su vez puede actualizar las tablas de resumen. En cierto sentido, esta solución es similar al n. ° 3 anterior, pero tendré un mejor control sobre estos desencadenantes ya que se implementarán en PHP.
Consideraciones de implementación:
completo sigue reconstruyendo
que quieren evitar tener que reconstruir las tablas de resumen, la eficiencia, y sólo actualización para nuevos datos. Pero en caso de que algo salga mal, necesito la capacidad de reconstruir la tabla de resumen desde cero utilizando los datos existentes en las tablas principales.
Haciendo caso omiso de actualizar/eliminar en datos antiguos
Algunos resúmenes pueden asumir que los registros anteriores no serán actualizados o borrados, pero se insertarán sólo nuevos registros. El proceso de resumen puede ahorrar mucho trabajo al asumir que no es necesario verificar actualizaciones en datos anteriores.
Pero, por supuesto, esto no se aplicará a todas las tablas.
Mantener un registro de
Vamos a suponer que no voy a tener acceso a, o no quieren utilizar los registros de MySQL binarios.
Para resumir los datos nuevos, el proceso de resumen solo necesita recordar los últimos ID de la clave principal para los últimos registros que resumió. La próxima vez que se ejecute, puede resumir todo después de esa identificación. Sin embargo, para realizar un seguimiento de los registros anteriores que se han actualizado/eliminado, necesita otro registro para que pueda retroceder y volver a resumir esos datos.
Le agradecería cualquier tipo de estrategias, sugerencias o enlaces que pueden ayudar. ¡Gracias!
Las vistas materializadas son vistas que pueden indexarse (denominadas "vistas indizadas" en la terminología de TSQL/SQL Server). Están notoriamente restringidos en funcionalidad, y MySQL no los admite. MySQL apenas admite vistas no materializadas, comparando la funcionalidad con otros proveedores. Oracle es el único otro DB que conozco que admite vistas materializadas, además de SQL Server. Esperaría que DB2 lo haga, pero PostgreSQL no. –