PostgreSQL
 sql >> Base de données >  >> RDS >> PostgreSQL

Utilisation d'un dictionnaire pour passer des paramètres à l'instruction postgresql en python

Veuillez utiliser une requête paramétrée comme décrit dans la documentation

Puisque vous avez déjà un dict, vous pouvez faire :

sql_data_sample = """select * from %(table_name)s
           where dt = %(date_from)s
           and target in ('ACTIVE')
           ----------------------------------------------------
           union all
           ----------------------------------------------------
           (select * from %(table_name)s
           where dt = %(date_to)s
           and target in (%(class_target)s));"""

cur.execute(sql_data_sample, query_params)

Je n'ai pas testé si cela fonctionne avec un dict odered, mais je pense que cela devrait. Sinon, vous pouvez faire de votre dict ordonné un dict normal avant de le transmettre en tant que mappage de paramètres.

MODIFIER À moins que vous n'ayez besoin de vos paramètres pour être un OrderedDict plus tard, utilisez un dict normal. Autant que je sache, vous avez uniquement opté pour un OrderedDict afin de préserver l'ordre des valeurs pour la list(query_params.values())[0] .

EDIT2 Les noms de table et les noms de champ ne peuvent pas être passés à l'aide de liaisons. Antoine Dusséaux a souligné dans cette réponse que psycopg2 offre un moyen plus ou moins sécurisé de le faire depuis la version 2.7.

from psycopg2 import sql

sql_data_sample = """select * from {0}
           where dt = %(date_from)s
           and target in ('ACTIVE')
           ----------------------------------------------------
           union all
           ----------------------------------------------------
           (select * from {0}
           where dt = %(date_to)s
           and target in (%(class_target)s));"""

cur.execute(sql.SQL(sql_data_sample)
                .format(sql.Identifier(query_params['table_name'])), 
            query_params)

Vous devrez peut-être supprimer le table_name à partir de votre dict, je ne sais pas comment psycopg2 réagit sur des éléments supplémentaires dans le dict des paramètres et je ne peux pas le tester pour le moment.

Il convient de souligner que cela pose toujours le risque d'injection SQL et doit être évité sauf en cas d'absolue nécessité. Normalement, les noms de table et de champ sont une partie plutôt fixe d'une chaîne de requête.

Voici la documentation pertinente pour sql modules .