2012-09-11 19 views
6

¿Está bien utilizar una sola conexión MySQLdb para múltiples transacciones sin cerrar la conexión entre ellas? En otras palabras, algo como esto:MySQLdb con transacciones múltiples por conexión

conn = MySQLdb.connect(host="1.2.3.4", port=1234, user="root", passwd="x", db="test") 

for i in range(10): 
    try: 
     cur = conn.cursor() 
     query = "DELETE FROM SomeTable WHERE ID = %d" % i 
     cur.execute(query) 
     cur.close() 
     conn.commit() 

    except Exception: 
     conn.rollback() 

conn.close() 

Parece que funciona bien, pero solo quería volver a comprobarlo.

+0

Lástima que no haya dejado su error. Realmente me confundí antes de leer las revisiones porque no veía cuál era el malentendido del que hablaba Martijn Pieters. –

Respuesta

15

Creo que hay un malentendido acerca de lo que constituye una transacción aquí.

Su ejemplo abre una conexión, luego ejecuta una transacción en ella. Ejecuta varias instrucciones SQL en esa transacción, pero la cierra completamente después de la confirmación. Por supuesto, eso está más que bien.

La ejecución de múltiples transacciones (en lugar de sólo las sentencias SQL), se ve así:

conn = MySQLdb.connect(host="1.2.3.4", port=1234, user="root", passwd="x", db="test") 

for j in range(10): 
    try: 
     for i in range(10): 
      cur = conn.cursor() 
      query = "DELETE FROM SomeTable WHERE ID = %d" % i 
      cur.execute(query) 
      cur.close() 
     conn.commit() 
    except Exception: 
     conn.rollback() 

conn.close() 

El código anterior se compromete 10 transacciones, cada uno compuesto por 10 individuales delete.

Y sí, debería poder volver a utilizar la conexión abierta para eso sin problemas, siempre que no comparta esa conexión entre subprocesos.

Por ejemplo, SQLAlchemy reutiliza las conexiones uniéndolas, distribuyendo las conexiones abiertas según sea necesario para la aplicación. Se ejecutan nuevas transacciones y nuevas declaraciones en estas conexiones a lo largo de la vida útil de una aplicación, sin necesidad de cerrarlas hasta que se cierre la aplicación.

+0

Sí, tienes razón. He estropeado mi ejemplo mientras lo riego para publicarlo. Lo arreglaré. – d512

+0

¿Cuál sería el problema al compartir conexiones entre hilos en mi escenario? – d512

+2

@ user1334007: De la [documentación de MySQLdb] (http://mysql-python.sourceforge.net/MySQLdb.html): * "Si permite que dos subprocesos usen una conexión simultáneamente, es probable que la biblioteca cliente MySQL se agote y muera. Usted ha sido advertido."*. –

0

Sería mejor construir primero una cadena de consulta y luego ejecutar esa sola instrucción de MySQL. Por ejemplo:

query = "DELETE FROM table_name WHERE id IN (" 
for i in range(10): 
    query = query + "'" + str(i) + "', " 
query = query[:-2] + ')' 

cur = conn.cursor() 
cur.execute(query) 
+0

Eso es más eficiente, pero hay razones por las que no lo estoy haciendo de esa manera. – d512

+0

Alight, solo revisando. –

Cuestiones relacionadas