2

我正在使用pg8000通过 Python 连接到 PostgreSQL 数据库。我希望能够通过以下cursor.execute方法将日期作为参数发送:

def info_by_month(cursor, year, month):
    query = """
    SELECT *
    FROM info
    WHERE date_trunc('month', info.created_at) =
          date_trunc('month', '%s-%s-01')
    """
    cursor.execute(query, (year, month))
    return cursor

这将引发错误:InterfaceError: '%s' not supported in a quoted string within the query string。可以使用 Python 的字符串格式在其中插入日期。使用字符串格式化迷你语言提供了一种数据验证措施来防止 SQL 注入攻击,但它仍然很丑陋。

def info_by_month(cursor, year, month):
    query = """
    SELECT *
    FROM info
    WHERE date_trunc('month', info.created_at) =
          date_trunc('month', '{:04}-{:02}-01')
    """.format(year, month)
    cursor.execute(query)
    return cursor

如何将带引号的字符串发送到cursor.execute方法中?

4

2 回答 2

1

format提前做,然后将结果字符串传递给execute. 这样可以避免SQL 注入的可能性,但仍然可以获得所需的格式。

例如查询变为:

query = """
    SELECT *
    FROM info
    WHERE date_trunc('month', info.created_at) =
          date_trunc('month', %s)"""

然后formatandexecute变成:

dateStr = "{:04}-{:02}-01".format(year, month)
cursor.execute(query, dateStr)

我使用psycopg2,但似乎pg8000遵循相同的DBI标准,所以我希望这也适用于pg8000

于 2015-01-27T00:01:34.910 回答
0

可以通过连接来做到这一点,这会损害可读性。

query = """
  SELECT *
  FROM info
  WHERE date_trunc('month', info.created_at) =
        date_trunc('month', %s || '-' || %s || '-01')
"""
cursor.execute(query, (year, month))
于 2015-01-27T01:53:56.213 回答