0
votes

Python / MySQL Comment insérer une chaîne à l'aide d'une variable, continue de changer "True" à 1

J'ai une table appelée LED_Status et un champ appelé "Test_led": xxx

Je tente de saisir une chaîne de "true" ou "false" (pas int 1 ou 0 ) Avec le code suivant: xxx

appelé à partir de ce script: xxx

Cependant, chaque fois que j'exécute le script change mon "vrai" à un 1 et mon "faux" à un 0 0.

Je passe à partir d'un fichier plat vers une base de données et tout mon code (4000 lignes de celui-ci) utilise " Vrai "et" False "Alors je ne veux vraiment pas avoir à la réécrire juste d'utiliser 1 et 0 par opposition à" vrai "et" faux ".

Toutes les pensées seraient grandement appréciées.


4 commentaires

Deux choses importantes: (1) Vous n'utilisez pas le formatage de chaîne % sur SQL, elle conduit à des vulnérabilités d'injection SQL (2) diviser les données et sa représentation: 0 / 1 ou dans python false / true sont les données utilisées pour stocker et traiter dans des ordinateurs, les chaînes "true" et "faux" sont comment vous présentez-le aux humains.


Merci @klausd. C'était ma compréhension que% s est la méthode correcte et que le curseur.execute protège spécifiquement contre les problèmes d'injection SQL. Les messages sur Stack Exchange m'ont pointé dans cette direction. Cette information est-elle incorrecte? Deuxièmement, comme je l'ai dit ci-dessus, je passe d'un fichier plat qui utilise une représentation vraie / fausse et je ne voulais vraiment pas réécrire tout le code à 0/1 lorsque j'ai déménagé dans une conception de la base de données, d'où la raison pour laquelle je veux coller avec TRUE / FAUX COMME A VARCHAR au lieu de 0/1 comme un peu ou un ministère.


La différence importante est le % entre la chaîne et les arguments. Il doit être une virgule pour être en sécurité.


@Klausd. Ah !!! Je pensais au mauvais%! Je vais lire plus sur cela et le changer.


3 Réponses :


1
votes

MySQL n'a pas de type booléen (TRUE / FAUX), ils sont automatiquement interprétés (et stockés) comme 0/1 (dans votre schéma ci-dessus, vous indiquez même clairement que vous souhaitez que vous souhaitiez des tinyints, et non des INT de 32 bits réguliers). Rien que vous ne puissiez faire à ce sujet!

Si vous souhaitez stocker la valeur littérale "true" / "false", vous devez utiliser Varcharchar (5) Type de colonne.

Note latérale: La valeur par défaut de ces colonnes doit être 0 ou 1, soit nullable - vous devez définir leur valeur par défaut sur NULL et la colonne non nullable, ce qui peut entraîner des erreurs sur la voie.


7 commentaires

J'utilise un Varchar (5)! Si vous regardez ma table ci-dessus, Test_led est le type Varchar (5).


@Richard Vous n'étiez pas à l'époque que j'ai écrit la réponse à cela. Il montre dans les révisions de votre message ...


En fait, le test_led a toujours été un varchar (5). Cela ne fonctionne toujours pas.


def get_led_status (LED): LED_Status = read_database_value ("LED_Status", LED) LED_Status = (LED_Status [0]) Retournez LED_Status


Désolé, je ne sais pas comment formater le code dans un commentaire :-)


@Richard met à jour la question avec toutes les données pertinentes, d'autres personnes peuvent vouloir le voir. Qu'est-ce que la valeur de la base de données LIRE est alors? Etc. Essayez de simplifier votre code et d'afficher tout ce qui est pertinent (mais pas une seule ligne de plus). Je n'ai aucune idée de ce qui est dans la piscine_running, cela pourrait être n'importe quoi.


Fera, j'essayais de la garder minimale que possible. Pool_Running est présenté dans le poste initial. Je vais mettre à jour la question!



0
votes

Comme @frrsechet Réponse a souligné, dans SQL, vous n'avez que 0/1 représentation de Boolean. Si vous voulez des chaînes vraies / fastes, vous devez modifier le type de colonne en chaîne / caractère (5).

Autre option est, si vous utilisez une fonction commune pour extraire / mettre à jour la valeur de la colonne, vous pouvez définir la valeur de la valeur de la valeur à l'intérieur de cette fonction qui convertit true / false au 1/0 et inversement.


1 commentaires

J'utilise un Varchar (5)! Si vous regardez ma table ci-dessus, Test_led est le type Varchar (5).



0
votes

Merci à tous ceux qui ont fourni une contribution. Après un lot em> de creuser, j'ai compris mon problème. Apparemment, vous ne pouvez pas paramétrer un nom de table dans une déclaration préparée qui est exactement ce que j'essayais de faire ci-dessus. Poste où j'ai trouvé la réponse @Conpice Le compilateur était mort avec cette déclaration.

Le problème était dans mon wreck_database_value () code> fonction. C'est la fonction correcte qui fonctionne au besoin: p> xxx pré>

le gros changement: p>

de: curseur.execute (("Mettre à jour% s défini% s =% s")% (tableau, champ, valeur)) code> p>

à ceci: p>

sql_update = "UPDATE " + table + " SET " + column + " = %s"
cursor.execute(sql_update, (value,))


2 commentaires

J'allais 100% de dire que ce matin, lors de la lecture de votre code, des accessoires pour le comprendre vous-même. Comme mentionné dans le lien de ma réponse, c'est vrai dans n'importe quel cas de lettre est converti en 1. Votre requête était "Mettre à jour LED_Status Set TRUE", qui est lue comme 1, pas comme la chaîne "vraie", car elle n'est pas enveloppée dans des guillemets . Un "Select Test_led de Led_Status" vous aurait aidé à déboguer plus rapidement. Note latérale: il est recommandé d'utiliser des déclarations préparées plutôt que d'insérer des chaînes dans une requête, pour des raisons de sécurité, mais aussi pour la raison pour laquelle vous avez vécu ici.


Exemple: Et si au lieu de "vrai", quelqu'un a écrit quelque chose dans le sens de "1; Drop Database;" ...