web-dev-qa-db-fra.com

python mysql.connector DictCursor?

Dans Python mysqldb je pourrais déclarer un curseur comme curseur de dictionnaire comme ceci:

cursor = db.cursor(MySQLdb.cursors.DictCursor) 

Cela me permettrait de référencer des colonnes dans la boucle cursor par nom comme ceci:

for row in cursor:   # Using the cursor as iterator 
    city = row["city"]
    state = row["state"]

Est-il possible de créer un curseur de dictionnaire à l'aide de ce connecteur MySQL? http://dev.mysql.com/doc/connector-python/en/connector-python-example-cursor-select.html

Leur exemple ne renvoie qu'un Tuple.

J'imagine que les créateurs de MySQL finiraient par le faire pour nous?

17
panofish

Une solution possible consiste à sous-classer la classe MySQLCursor comme ceci:

class MySQLCursorDict(mysql.connector.cursor.MySQLCursor):
    def _row_to_python(self, rowdata, desc=None):
        row = super(MySQLCursorDict, self)._row_to_python(rowdata, desc)
        if row:
            return dict(Zip(self.column_names, row))
        return None

db = mysql.connector.connect(user='root', database='test')

cursor = db.cursor(cursor_class=MySQLCursorDict)

Maintenant, la méthode _row_to_python() renvoie un dictionary au lieu d'un Tuple.

J'ai trouvé cela sur le forum mysql, et je pense qu'il a été posté par les développeurs mysql eux-mêmes. J'espère qu'ils l'ajouteront au package du connecteur mysql un jour.

J'ai testé cela et cela fonctionne.

MISE À JOUR: Comme mentionné ci-dessous par Karl M.W ... cette sous-classe n'est plus nécessaire dans la v2 du mysql.connector. Le mysql.connector a été mis à jour et vous pouvez maintenant utiliser l'option suivante pour activer un curseur de dictionnaire.

cursor = db.cursor(dictionary=True)
11
panofish

Selon cet article, il est disponible en passant 'dictionary = True' au constructeur du curseur: http://dev.mysql.com/doc/connector-python/en/connector-python-api-mysqlcursordict. html

alors j'ai essayé:

cnx = mysql.connector.connect(database='bananas')
cursor = cnx.cursor(dictionary=True)

et a obtenu: TypeError: cursor () a obtenu un argument de mot clé inattendu "dictionnaire"

et j'ai essayé:

cnx = mysql.connector.connect(database='bananas')
cursor = cnx.cursor(named_Tuple=True)

et a obtenu: TypeError: cursor () a obtenu un argument de mot clé inattendu 'named_Tuple'

et j'ai aussi essayé celui-ci: cursor = MySQLCursorDict(cnx)

mais en vain. De toute évidence, je suis sur la mauvaise version ici et je soupçonne que nous devons simplement être patients comme le document à http://downloads.mysql.com/docs/connector-python-relnotes-en.a4.pdf suggère que ces nouvelles fonctionnalités sont en phase alpha au moment de l'écriture.

20
J1MF0X

Cet exemple fonctionne:

cnx = mysql.connector.connect(database='world')
cursor = cnx.cursor(dictionary=True)
cursor.execute("SELECT * FROM country WHERE Continent = 'Europe'")

print("Countries in Europe:")
for row in cursor:
    print("* {Name}".format(Name=row['Name']

Gardez à l'esprit que dans cet exemple, 'Name' est spécifique au nom de colonne de la base de données référencée.

De plus, si vous souhaitez utiliser des procédures stockées, faites-le à la place:

cursor.callproc(stored_procedure_name, args)
result = []
for recordset in cursor.stored_results():
    for row in recordset:
        result.append(dict(Zip(recordset.column_names,row)))

stored_procedure_name est le nom de la procédure stockée à utiliser et args est la liste des arguments de cette procédure stockée (laissez ce champ vide comme [] si aucun argument à transmettre).

Ceci est un exemple de la documentation MySQL trouvée ici: http://dev.mysql.com/doc/connector-python/en/connector-python-api-mysqlcursordict.html

8
Blairg23

En utilisant Python 3.6.2 et MySQLdb version 1.3.10, j'ai obtenu ceci pour fonctionner avec:

import MySQLdb
import MySQLdb.cursors

...

conn = MySQLdb.connect(Host='...', 
                       <connection info>, 
                       cursorclass=MySQLdb.cursors.DictCursor)

try:
    with conn.cursor() as cursor:
        query = '<SQL>'
        data = cursor.fetchall()
        for record in data:
            ... record['<field name>'] ...

finally:
    conn.close()

J'utilise PyCharm, et j'ai simplement creusé dans les modules MySQLdb connections.py et cursors.py.

4
KenH