if count == 1:
cursor.execute("SELECT * FROM PacketManager WHERE ? = ?", filters[0], parameters[0])
all_rows = cursor.fetchall()
elif count == 2:
cursor.execute("SELECT * FROM PacketManager WHERE ? = ? AND ? = ?", filters[0], parameters[0], filters[1], parameters[1])
all_rows = cursor.fetchall()
elif count == 3 :
cursor.execute("SELECT * FROM PacketManager WHERE ? = ? AND ? = ? AND ? = ?", filters[0], parameters[0], filters[1], parameters[1], filters[2], parameters[2])
all_rows = cursor.fetchall()
这是我程序中的代码段。我打算做的是在查询中传递列名和参数。
filters数组包含列名,参数数组包含参数。计数是用户设置的过滤器数量。过滤器和参数数组已准备就绪,没有问题。我只需要将它传递给查询即可执行。这给了我一个错误" TypeError:函数最多需要2个参数"
答案 0 :(得分:8)
您不能使用SQL参数来插入列名。您必须对这些部分使用经典字符串格式。这是SQL参数的点;它们引用值,因此它们不可能被解释为SQL语句或对象名称。
以下内容,使用字符串格式的列名称有效,但 100%确定,filters[0]
值不是来自用户输入:
cursor.execute("SELECT * FROM PacketManager WHERE {} = ?".format(filters[0]), (parameters[0],))
您可能希望根据一组允许的列名验证列名,以确保不会发生注入。
答案 1 :(得分:4)
您只能使用?
设置参数,而不能使用表名或列名设置参数。
您可以使用预定义的查询构建一个dict。
queries = {
"foo": "SELECT * FROM PacketManager WHERE foo = ?",
"bar": "SELECT * FROM PacketManager WHERE bar = ?",
"foo_bar": "SELECT * FROM PacketManager WHERE foo = ? AND bar = ?",
}
# count == 1
cursor.execute(queries[filters[0], parameters[0])
# count == 2
cursor.execute(queries[filters[0] + "_" + queries[filters[1], parameters[0])
这种方法可以让您在filters[0]
中保存SQL注入。