IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

wxPython Discussion :

syntaxe MySQLdb


Sujet :

wxPython

  1. #1
    Membre averti
    Homme Profil pro
    retraité, actif ??
    Inscrit en
    Mars 2008
    Messages
    23
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Manche (Basse Normandie)

    Informations professionnelles :
    Activité : retraité, actif ??
    Secteur : Enseignement

    Informations forums :
    Inscription : Mars 2008
    Messages : 23
    Par défaut syntaxe MySQLdb
    Bonjour,
    J'utilise MySQLdb dans un contexte wxPython pour l'interface.
    pour tester les syntaxes, j'ai cette base MySQL simple:
    base: uneligne -> table: laligne-> colonnes:Id, laphrase (varchar(50))

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    def On_enregistrer(self, evt):
               une_ligne = self.texte.GetValue()
                qry = "INSERT INTO laligne(laphrase) VALUES (%s)"
                self.curs_db.execute(qry, une_ligne)
    Ce que je cherche, c'est de paraméter %s le nom de la table (ici la ligne)car cette syntaxe, lorsqu'elle sera correcte, passera dans un autre programme; là les noms des tables seront à choisir, et le nom choisi sera passé en paramètre à Insert ou update dans mysql.
    Pour le moment, cette syntaxe ne retourne qu'erreurs.


    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    def On_enregistrer(self, evt):
        une_ligne = self.texte.GetValue()
        table ='laligne'
        seq = "insert into %s  values(%s, %s) "
        self.curs_db.execute(seq, (table, 0, une_ligne))
    raise error, errorvalue, ... et la célèbre 1064...

    De grands espoirs pour une (LA) réponse...

    Pancrace (qui ne sait comment activer la balise html)

  2. #2
    Expert éminent
    Homme Profil pro
    Architecte technique retraité
    Inscrit en
    Juin 2008
    Messages
    21 688
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Manche (Basse Normandie)

    Informations professionnelles :
    Activité : Architecte technique retraité
    Secteur : Industrie

    Informations forums :
    Inscription : Juin 2008
    Messages : 21 688
    Par défaut
    Salut,

    Plusieurs choses.
    1. La construction de la chaine de caractères passé comme statement à exécute,
    2. Celle ci construite comment passer les paramètre.

    La construction est "compliquée" car comme vous voulez faire varier le nom de la table, la construction de la chaîne de caractère à passer à exécute doit se faire en deux temps:
    1. assignation
    2. affectation du nom de la table
    ... et comme MySQLDB semble utiliser %s pour les paramètres de la requêtes et que vous avez eu l'idée d'utiliser cette forme de paramètrage des chaines de caractères Python....
    On peut s'en sortir ainsi:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    >>> name = 'table_name'
    >>> table_name = 'table_name'
    >>> stmt_fmt = 'INSERT INTO %(table_name)s VALUES(%%s, %%s)'
    >>> stmt = stmt_fmt % vars()
    >>> print (stmt)
    INSERT INTO table_name VALUES(%s, %s)
    Mais plutôt que de doubler les %, on peut choisir une autre façon de formatter la chaine Python:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    >>> stmt_fmt = 'INSERT INTO {table_name:s} VALUES(%s, %s)'
    >>> stmt = stmt_fmt.format(**vars())
    >>> print (stmt)
    INSERT INTO table_name VALUES(%s, %s)
    Pour ce qui est de passer les paramètres, c'est une autre histoire!
    Lorsque vous écrivez:
    self.curs_db.execute(seq, (table, 0, une_ligne))
    recoit: "insert into %s values(%s, %s) ", (table, 0, une_ligne)
    qu'il ne sait pas traiter parce que s'il sait interprêter les %s de VALUES, ce n'est pas Python et le boulot consistant à remplacer le nom de la table, il ne sait pas le faire...
    De plus VALUES(%s, %s) dit "liste de uplets à 2 paramètres" alors que vous proposez un uplet à 3 paramètres!
    La forme:
    self.curs_db.execute(stmt, [(0, une_ligne), ])
    avec stmt la chaine construite "avant" devrait mieux aller.

    Cordialement,
    - W
    Architectures post-modernes.
    Python sur DVP c'est aussi des FAQs, des cours et tutoriels

  3. #3
    Membre averti
    Homme Profil pro
    retraité, actif ??
    Inscrit en
    Mars 2008
    Messages
    23
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Manche (Basse Normandie)

    Informations professionnelles :
    Activité : retraité, actif ??
    Secteur : Enseignement

    Informations forums :
    Inscription : Mars 2008
    Messages : 23
    Par défaut
    Bonjour,
    grand merci wiztricks pour cette réponse et sa rapidité.
    Je vais reprendre et relire votre réponse avec crayon et papier.

    J'ai poursuivi à tâtons, les combinaisons possible, mais dans Pyshell avec MySLdb.
    Même base que cité en premier.

    curs.execute("select * from laligne")
    19L
    C'est BON
    Comme les erreurs précédentes invitaient à aller faire un tour dans /..../python2.6/MySQLdb/cursors.py, j'ysuis allé (nb: je suis sous Squeeze)

    Là le commentaire dit que args doit être une séquence et %s utilisé.
    d'où
    table = 'laligne'
    curs.execute("select * from %s", (table))
    Et c'est reparti pour un air connu..

    Pancrace
    Je re "DIVE into Python"

  4. #4
    Membre averti
    Homme Profil pro
    retraité, actif ??
    Inscrit en
    Mars 2008
    Messages
    23
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Manche (Basse Normandie)

    Informations professionnelles :
    Activité : retraité, actif ??
    Secteur : Enseignement

    Informations forums :
    Inscription : Mars 2008
    Messages : 23
    Par défaut
    Re...

    Je pensais que les %s étaient remplacés dans l'ordre de leur rencontre, d'où le regroupement dans une séquence..

    J'ai repris vos indications, cela va parfaitement..

    Il ne me reste qu'à rechercher le pourquoi de cette syntaxe, qui va au delà de celle que j'utilise pour les simple VALUES et le %s

    Un grand merci wiztricks, pour votre aide.

    cordialement

    Pancrace

  5. #5
    Expert éminent
    Homme Profil pro
    Architecte technique retraité
    Inscrit en
    Juin 2008
    Messages
    21 688
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Manche (Basse Normandie)

    Informations professionnelles :
    Activité : Architecte technique retraité
    Secteur : Industrie

    Informations forums :
    Inscription : Juin 2008
    Messages : 21 688
    Par défaut
    Salut,

    Je pensais que les %s étaient remplacés dans l'ordre de leur rencontre, d'où le regroupement dans une séquence..
    C'est ce qu'il fait lorsqu'on lui passe:
    "INSERT INTO %s VALUES(%s, %s)", (table, 0, une_ligne)
    Mais çà se passe "mal"...

    Alors que:
    "INSERT INTO laligne VALUES(%s, %s)", (0, une_ligne)
    se passe mieux.

    La différence étant que cette "formule" mets en route une mécanique plus ou moins compliquée de ré-écriture des paramètres exprimés en types Python sous une forme comestible par le SGDB.
    C'est l'API qui s'en débrouille.
    Mais intuitivement, mettre le nom de la table dans la lessiveuse ne peut qu'être "problème"... et il est préférable de "séparer"

    Si vous relisez le code de cursors.py, c'est vrai que çà dit:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
            """Execute a query.
            
            query -- string, query to execute on server
            args -- optional sequence or mapping, parameters to use with query.
     
            Note: If args is a sequence, then %s must be used as the
            parameter placeholder in the query. If a mapping is used,
            %(key)s must be used as the placeholder.
     
            Returns long integer rows affected, if any
     
            """
    On peut se dire "chouette".
    Mais quand on lit le code, on voit la lessiveuse arriver dans le cas ou on passe des paramètres:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
            try:
                if args is None:
                    r = self._query(query)
                else:
                    r = self._query(query % self.connection.literal(args))
    => que l'API fasse ce qu'elle doit pour convertir les données... pas de problème. Mais lui déléguer la construction de la "query" en poussant le nom de la table dans les "values" est plutôt risqué.
    nota, suivant comment est réalisée l'API çà pourrait "fonctionner" mais les objets (query et args) étant de nature différente, les mélanger n'est pas très sain.

    - W
    Architectures post-modernes.
    Python sur DVP c'est aussi des FAQs, des cours et tutoriels

  6. #6
    Membre averti
    Homme Profil pro
    retraité, actif ??
    Inscrit en
    Mars 2008
    Messages
    23
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Manche (Basse Normandie)

    Informations professionnelles :
    Activité : retraité, actif ??
    Secteur : Enseignement

    Informations forums :
    Inscription : Mars 2008
    Messages : 23
    Par défaut
    Bonjour,

    Je viens de lire votre message à propos des "%s"..
    Pour le moment, je vais poursuivre le développement de la geston de la base de données d'articles de presse que j'ai archivé, votre réponse me permet d'avoir une table par année et non une base par année.

    Je conserve dans une case "(my)self.memory" cette question de la conversion des données. Sachez aussi que je ne suis pas un "pythoniste" chevronné, j'y accède par essais successifs, c'est le bon côté des langages interprétés et pioche dans "Python en concentré" qu'il serait peut-être bon de diluer parfois.

    Pancrace

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. [syntaxe] Gerer les variables dans une requete
    Par rastapopulos dans le forum MS SQL Server
    Réponses: 12
    Dernier message: 15/04/2003, 12h53
  2. Syntaxe requete
    Par Chipolata dans le forum Langage SQL
    Réponses: 2
    Dernier message: 28/03/2003, 14h22
  3. [Syntaxe] Action simultanée sur plusieurs élements
    Par FranT dans le forum Composants VCL
    Réponses: 2
    Dernier message: 20/03/2003, 20h20
  4. Syntaxe TASM <-> MASM
    Par LFC dans le forum Assembleur
    Réponses: 3
    Dernier message: 28/02/2003, 15h56
  5. [VB6] [Syntaxe] Fonction renvoyant un tableau d'objets
    Par Troopers dans le forum VB 6 et antérieur
    Réponses: 2
    Dernier message: 18/10/2002, 15h33

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo