首页 文章

如何在Python中的SQL语句中使用变量?

提问于
浏览
64

好的,所以我不是那种经验丰富的Python .

我有以下Python代码:

cursor.execute("INSERT INTO table VALUES var1, var2, var3,")

其中 var1 是整数, var2var3 是字符串 .

如何在没有python的情况下编写变量名,包括它们作为查询文本的一部分?

4 回答

  • 17
    cursor.execute("INSERT INTO table VALUES (%s, %s, %s)", (var1, var2, var3))
    

    请注意,参数作为元组传递 .

    数据库API可以正确转义和引用变量 . 注意不要使用字符串格式化运算符( % ),因为

    • 它没有做任何转义或引用 .

    • 很容易受到不受控制的字符串格式攻击,例如SQL injection .

  • 68

    Python DB-API的不同实现允许使用不同的占位符,因此您需要找出您正在使用的占位符 - 它可能是(例如使用MySQLdb):

    cursor.execute("INSERT INTO table VALUES (%s, %s, %s)", (var1, var2, var3))
    

    或(例如,使用Python标准库中的sqlite3):

    cursor.execute("INSERT INTO table VALUES (?, ?, ?)", (var1, var2, var3))
    

    或者其他人(在 VALUES 之后你可以 (:1, :2, :3) ,或"named styles" (:fee, :fie, :fo)(%(fee)s, %(fie)s, %(fo)s) ,你传递一个字典而不是 Map 作为第二个参数到 execute ) . 检查您正在使用的DB API模块中的 paramstyle 字符串常量,并在http://www.python.org/dev/peps/pep-0249/查找paramstyle以查看所有参数传递样式是什么!

  • 24

    很多种方法 . DON'T 在实际代码中使用最明显的一个( %s% ),它对attacks开放 .

    这里复制粘贴_37634:

    # Never do this -- insecure!
    symbol = 'RHAT'
    c.execute("SELECT * FROM stocks WHERE symbol = '%s'" % symbol)
    
    # Do this instead
    t = ('RHAT',)
    c.execute('SELECT * FROM stocks WHERE symbol=?', t)
    print c.fetchone()
    
    # Larger example that inserts many records at a time
    purchases = [('2006-03-28', 'BUY', 'IBM', 1000, 45.00),
                 ('2006-04-05', 'BUY', 'MSFT', 1000, 72.00),
                 ('2006-04-06', 'SELL', 'IBM', 500, 53.00),
                ]
    c.executemany('INSERT INTO stocks VALUES (?,?,?,?,?)', purchases)
    

    More examples if you need:

    # Multiple values single statement/execution
    c.execute('SELECT * FROM stocks WHERE symbol=? OR symbol=?', ('RHAT', 'MSO'))
    print c.fetchall()
    c.execute('SELECT * FROM stocks WHERE symbol IN (?, ?)', ('RHAT', 'MSO'))
    print c.fetchall()
    # This also works, though ones above are better as a habit as it's inline with syntax of executemany().. but your choice.
    c.execute('SELECT * FROM stocks WHERE symbol=? OR symbol=?', 'RHAT', 'MSO')
    print c.fetchall()
    # Insert a single item
    c.execute('INSERT INTO stocks VALUES (?,?,?,?,?)', ('2006-03-28', 'BUY', 'IBM', 1000, 45.00))
    
  • 48

    http://www.amk.ca/python/writing/DB-API.html

    当你只是在你的语句中附加变量值时要小心:想象一下用户自己命名 ';DROP TABLE Users;' - 这就是你需要使用sql escaping的原因,当你以一种体面的方式使用cursor.execute时,Python会为你提供 . 网址中的示例是:

    cursor.execute("insert into Attendees values (?, ?, ?)", (name,
    seminar, paid) )
    

相关问题