¿Guardar declaraciones SQL en una tabla para ejecutarlas después es una mala idea?

21

¿Es una mala idea guardar instrucciones SQL en una tabla MySQL para ejecutarlas más tarde? Las instrucciones SQL estarán listas para su ejecución, es decir, no habrá parámetros para intercambiar ni nada, por ejemplo DELETE FROM users WHERE id=1.

Supongo que estoy siendo flojo, pero pensé en esta idea porque estoy trabajando en un proyecto que requerirá bastantes trabajos cron que ejecutarán periódicamente sentencias SQL.

Amustom Rustom
fuente
Debe aclarar si tiene la intención de ejecutar estas sentencias SQL una vez o si desea ejecutar el mismo conjunto de sentencias repetidamente.
GrandmasterB
10
Toda esta pregunta parece una de esas situaciones en las que el enfoque fundamental es incorrecto. Pero es difícil decir exactamente qué, porque sabemos muy poco sobre el espacio del problema.
Erick Robertson

Respuestas:

46

Es seguro, si eso es lo que estás preguntando. Siempre que sea tan cuidadoso con su seguridad como lo es con la seguridad de sus datos.

Pero no reinvente la rueda, los procedimientos almacenados SON bits de SQL almacenados en una tabla. Y apoyan, más aún alientan, la parametrización.

También tenga en cuenta que puede simplificar su seguridad Y reducir el número de puntos de falla Y reducir las comunicaciones de red utilizando el Programador de eventos MySql en lugar de cron.

Otras bases de datos tienen equivalentes a estos, por una buena razón. No eres el primero en necesitar esta funcionalidad.

pdr
fuente
1
+1 al usar el planificador. Limitar el acceso del planificador a solo los procesos es mejor que el acceso a la tabla.
JeffO
Pero, ¿qué sucede si necesita crear dinámicamente estas consultas, digamos desde una interfaz de usuario? Por ejemplo, si permite que los usuarios administradores establezcan dinámicamente reglas de acceso a contenidos web basados ​​en consultas complejas. No querrá que la interfaz de usuario cree un nuevo proceso en la base de datos. Creo que, en algunas circunstancias, las consultas almacenadas son mejores que los procs.
DiscípuloMichael
32

Si desea guardar las instrucciones SQL en una base de datos para su posterior ejecución, existe una mejor opción que ponerlas en una tabla: use la funcionalidad incorporada que se proporciona para este propósito específico. Póngalos en procedimientos almacenados.

Mason Wheeler
fuente
2
Entonces, ¿dónde almacena el trabajo cron la lista de procedimientos almacenados para ejecutar?
JeffO
1
esto puede ser útil stackoverflow.com/questions/6560639/… aunque no está usando cron
MetaFight
No sé lo que estaba pensando. Una lista de procesos podría ejecutarse desde un solo proceso, por lo que el trabajo cron solo necesita ejecutar uno.
JeffO
11

No, diría que no es una buena idea.

Significa que cada consulta / actualización "real" necesitará 2 aciertos en la base de datos: una para obtener la consulta / actualización "real" y otra para ejecutarla.

Esto puede no ser un gran problema en un sistema pequeño, pero cuantos más usuarios / transacciones obtenga su sistema, menos escalará.

¿Supongo que esto proviene de buscar una alternativa para incrustar SQL en su código?

Encapsular el SQL en un procedimiento almacenado como sugirió Mason Wheeler, sería una forma mucho mejor que esta idea.

ozz
fuente
+1, esta es la razón principal por la cual la solución de @Mason Wheeler es la correcta, simplemente se olvidó de resaltar eso. Aunque, en mi humilde opinión, no es el problema de rendimiento que veo aquí lo más importante: simplemente no hay necesidad de complicar las cosas extrayendo una declaración SQL de la base de datos y enviándola nuevamente para su ejecución.
Doc Brown
¿Por qué la lista de sentencias sql tiene que almacenarse en la misma base de datos / servidor, etc.?
JeffO
1
El OP es el que propone 2 hits en la base de datos. Yo digo que no debería hacerlo. Luego pregunta por qué tiene que ser la misma base de datos / servidor. Le pregunto quién dijo que sí. luego preguntas cómo más obtienes 2 hits en el DB. ¿Por qué no declaras tu pregunta real en lugar de lo que sea que estás haciendo?
ozz
1
@JeffO Incluso si se trata de una base de datos diferente, sigue siendo 2 consultas de base de datos para lo que debería ser 1 consulta, lo que es una ralentización innecesaria
Izkata
1
@Ozz: le da demasiado peso al aspecto de rendimiento de su respuesta: el rendimiento es probablemente descuidado en la mayoría de los escenarios del mundo real. Pero la necesidad de dos acciones (la primera para obtener la consulta / actualización "real", la segunda para ejecutarla) hace las cosas más complicadas de lo necesario.
Doc Brown
4

Lo siento, no creo que sea una buena idea.

Considere el caso donde cambia la tabla en cuestión. Digamos que su columna de identificación se renombra a new_id .

Además del cambio en sí, hay una versión de su código escrita para una versión antigua de la base de datos que ya no puede ejecutarse. Claro, es posible que sepa verificar en la tabla de códigos, pero no es obvio de inmediato para otra persona.

Para un cambio como el que he descrito, normalmente miraría archivos SQL independientes, procedimientos almacenados, disparadores, SQL en línea en el código del cliente (VB, C #, C ++, etc.) pero el último lugar en el que pensaría buscar está en las tablas de la base de datos. Aunque tal vez lo haga ahora! :)

Robbie Dee
fuente
2

Hay razones válidas para almacenar SQL en una tabla. El software con el que trabajo en el trabajo ahora incluye un sistema para generar documentos y los documentos deben incluir cálculos bastante complejos utilizando datos en una base de datos. Los documentos se actualizan con frecuencia, a menudo son significativamente diferentes en términos de los datos necesarios y los cálculos que deben realizarse. SQL se está utilizando, básicamente, como un lenguaje de secuencias de comandos para realizar estos cálculos y ese SQL se almacena en tablas que también almacenan otra información para estos documentos. Las personas que mantienen esos documentos no son programadores o DBA, pero están familiarizados con el esquema de la base de datos y son competentes con SQL. Sería una sobrecarga significativa para ellos mantener ese código SQL en forma de procedimientos almacenados.

Para lo que describió: "... un proyecto que requerirá bastantes trabajos cron que ejecutarán sentencias SQL periódicamente", las otras respuestas probablemente sean correctas al sugerir que utilizó procedimientos de almacenamiento, o el equivalente, para el DBMS que ' re usar.

Un buen criterio para decidir si es sensato almacenar SQL en una tabla versus en un procedimiento almacenado es determinar quién mantendrá ese SQL. Si los usuarios mantienen ese SQL, es decir, lo escriben y lo cambian cuando lo deseen, entonces puede estar perfectamente bien, y de hecho lo mejor, almacenar ese SQL en una tabla. Si los desarrolladores mantendrán ese SQL, entonces debe almacenarse en una forma que pueda actualizarse con sus procedimientos de construcción e implementación (con suerte automatizados), por ejemplo, almacenados como un objeto como un procedimiento almacenado en la base de datos.

Kenny Evitt
fuente
1
Gracias por la respuesta. Terminé usando eventos MySQL para programar las consultas para que se ejecuten. Muchas personas pensaron "el enfoque fundamental es incorrecto" :) cuando todo lo que necesitaba era ejecutar algunas declaraciones SQL después de 15 minutos de una acción específica del usuario.
Amged Rustom
2
@AmgadSuliman: es importante ser caritativo con todos, especialmente en los sitios de SE. Es bueno tener opiniones firmes, pero es demasiado fácil igualar los patrones contra los que disfrutamos inventando. Pero parte de ser caritativo con otros en estos sitios es proporcionar suficiente contexto; demasiado puede oscurecer la pregunta real, pero en general eso es bastante fácil de solucionar mediante la edición posterior.
Kenny Evitt
1

La salida fácil sería tener un archivo .ini u otro archivo de configuración para guardar las consultas. De esta manera, puede tenerlas en un solo lugar, cambiar cualquier cosa sin tener que acceder a la base de datos para hacerlo, no golpear la base de datos varias veces. y también es posible que desee / necesite en algún momento usar parámetros o agregar condiciones a sus consultas (aumente con cosas más complejas para un caso particular en su código).

Por supuesto, puede mantenerlos a nivel de base de datos (ya sea en una tabla o, mejor aún, como procedimientos almacenados), sin embargo, si es tan vago como yo ;-) pero también le preocupa el rendimiento, un archivo .ini y PHP ¡Amado método parse_ini para leerlo, es el camino a seguir (si vas a buscar otro lenguaje de programación, estás descubriendo enfoques similares)! Por lo general, leería este archivo en el gestor de arranque de la aplicación y lo mantendría en un objeto estático (tal vez con una capa de caché en la parte superior) para acelerar realmente las cosas si estamos hablando de una gran cantidad de consultas distintas.

Thyamarkos
fuente
1

Si solo necesita la instrucción SQL una vez, por ejemplo, si está haciendo cola en un montón de operaciones para realizar durante las horas libres, entonces sí, ponerlas en una tabla funcionará bien.

Si necesita ejecutar la misma instrucción SQL a intervalos específicos, entonces la ruta del procedimiento almacenado que otros han mencionado es probablemente una mejor opción para usted.

Dicho esto, lo que está preguntando es bastante inusual y puede ser una indicación de algún otro problema. Por ejemplo, si está esperando eliminar un usuario de una base de datos, puede ser mejor llamar a un script programado que realiza la operación a través del código de su aplicación, en lugar de registrar las declaraciones SQL reales. De esta manera, el SQL y el código nunca están fuera de sincronización.

Gran maestro B
fuente