You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用SQLAlchemy 2.0删除90天前数据遇参数错误如何解决?

问题

我正在学习SQLAlchemy,想要删除当前日期起算超过X天的旧数据。尝试执行以下代码:

from datetime import datetime, timedelta

import sqlalchemy

db_con_string = 'Driver={ODBC Driver 17 for SQL Server};Server=tcp...'
connection_url = sqlalchemy.engine.URL.create("mssql+pyodbc",
                                              query={"odbc_connect": db_con_string})
engine = sqlalchemy.create_engine(connection_url)

with engine.begin() as sql_conn:
    command = 'delete myschema.Logs where [DateTimeSent] < ?'
    params = ((datetime.utcnow() + timedelta(days=-90)), )
    sql_conn.execute(sqlalchemy.sql.text(command), params)

执行后报错:sqlalchemy.exc.ArgumentError: List argument must consist only of tuples or dictionaries
使用的是SQLAlchemy 2.0.23版本,该如何修复这个错误?

解决方案

这个错误的核心是参数传递格式不符合SQLAlchemy 2.0的要求,和datetime对象本身无关,以下是几种修复方式:

  • 简化参数为单层单元素元组:你当前的params是嵌套元组((datetime_obj,),),SQLAlchemy 2.0不接受这种嵌套结构,改成单层即可:

    params = (datetime.utcnow() + timedelta(days=-90), )
    sql_conn.execute(sqlalchemy.sql.text(command), params)
    
  • 用列表包裹参数:直接把参数放到列表中,也是符合要求的格式:

    params = [datetime.utcnow() + timedelta(days=-90)]
    sql_conn.execute(sqlalchemy.sql.text(command), params)
    
  • 使用命名参数(推荐,可读性更强):修改SQL语句为命名占位符,搭配字典传递参数,能避免位置参数的混淆:

    command = 'delete myschema.Logs where [DateTimeSent] < :cutoff_date'
    params = {"cutoff_date": datetime.utcnow() + timedelta(days=-90)}
    sql_conn.execute(sqlalchemy.sql.text(command), params)
    

注:Python datetime对象可以被SQLAlchemy 2.0自动转换为SQL Server对应的日期类型,无需额外处理。

内容的提问来源于stack exchange,提问作者Vitamin C

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.05 04:48:16