Psycopg2:如何使用 psycopg2 和 python 插入和更新冲突?

Abh*_*ngh 3 postgresql psycopg2

我正在使用 psycopg2 将命令插入 postgres 数据库,当出现冲突时,我只想更新其他列值。

这是查询:

        insert_sql = '''
        INSERT INTO tablename (col1, col2, col3,col4)
        VALUES (%s, %s, %s, %s) (val1,val2,val3,val4)
        ON CONFLICT (col1)
        DO UPDATE SET
        (col2, col3, col4)
        = (val2, val3, val4) ; '''

        cur.excecute(insert_sql)
Run Code Online (Sandbox Code Playgroud)

我想找出我做错的地方?我使用的变量 val1 , val2, val3 不是实际值。

Ion*_*cus 8

引用 psycopg2 的文档

警告 永远,永远,永远不要使用 Python 字符串连接 (+) 或字符串参数插值 (%) 将变量传递给 SQL 查询字符串。甚至不是在枪口下。

现在,对于 upsert 操作,您可以执行以下操作:

insert_sql = '''
    INSERT INTO tablename (col1, col2, col3, col4)
    VALUES (%s, %s, %s, %s)
    ON CONFLICT (col1) DO UPDATE SET
    (col2, col3, col4) = (EXCLUDED.col2, EXCLUDED.col3, EXCLUDED.col4);
'''
cur.execute(insert_sql, (val1, val2, val3, val4))
Run Code Online (Sandbox Code Playgroud)

请注意,查询的参数作为元组传递给execute语句(这确保 psycopg2 将负责使它们适应 SQL,同时保护您免受注入攻击)。

EXCLUDED位允许您重复使用这些值,而无需在 data 参数中指定它们两次。

  • 很有帮助!小注意事项 - 它应该是 (col2, col3, col4) = (EXCLUDED.col2, EXCLUDED.col3, EXCLUDED.col4); (2认同)

小智 7

使用:

INSERT INTO members (member_id, customer_id, subscribed, customer_member_id, phone, cust_atts) VALUES (%s, %s, %s, %s, %s, %s) ON CONFLICT (customer_member_id) DO UPDATE SET (phone) = (EXCLUDED.phone);
Run Code Online (Sandbox Code Playgroud)

我收到以下错误:

psycopg2.errors.FeatureNotSupported: source for a multiple-column UPDATE item must be a sub-SELECT or ROW() expression
LINE 1: ...ICT (customer_member_id) DO UPDATE SET (phone) = (EXCLUDED.p...
Run Code Online (Sandbox Code Playgroud)

更改为:

INSERT INTO members (member_id, customer_id, subscribed, customer_member_id, phone, cust_atts) VALUES (%s, %s, %s, %s, %s, %s) ON CONFLICT (customer_member_id) DO UPDATE SET (phone) = ROW(EXCLUDED.phone);
Run Code Online (Sandbox Code Playgroud)

解决了问题。