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

SQLAlchemy查询Access数据库日期条件语法错误求助

问题

我在Python中使用SQLAlchemy实现了如下查询:

url = URL.create(
                 drivername="access+pyodbc",
                 query={
                 "odbc_connect": connStr,
                 },
                 )
with create_engine(url).connect() as con:
     sql_get_anag = text(f"SELECT Tipo_Presenza FROM Presenza WHERE ID_Anagrafica = {IDValue} AND Giorno > {current_day_insert} AND Giorno < {current_day_insert_1}")
     Presenza_tab =  pd.read_sql_query(sql_get_anag, con)

执行后返回如下错误:

Exception has occurred: ProgrammingError
(pyodbc.ProgrammingError) ('42000', "[42000] [Microsoft][Driver ODBC Microsoft Access] Errore di sintassi (operatore mancante) nell'espressione della query 'ID_Anagrafica = 4 AND Giorno > 24-05-24 00:00:00 AND Giorno < 25-05-24 00:00:00'. (-3100) (SQLExecDirectW)")
[SQL: SELECT Tipo_Presenza FROM Presenza WHERE ID_Anagrafica = 4 AND Giorno > 24-05-24 00:00:00 AND Giorno < 25-05-24 00:00:00]
(Background on this error at: https://sqlalche.me/e/20/f405)
pyodbc.ProgrammingError: ('42000', "[42000] [Microsoft][Driver ODBC Microsoft Access] Errore di sintassi (operatore mancante) nell'espressione della query 'ID_Anagrafica = 4 AND Giorno > 24-05-24 00:00:00 AND Giorno < 25-05-24 00:00:00'. (-3100) (SQLExecDirectW)")

我认为是WHERE条件中的日期语法不正确,但不知道正确语法是什么。我尝试添加/移除日期参数的单引号但未成功,期望能正确执行该SELECT查询,恳请提供解决建议。


解决建议

核心问题

直接用f-string拼接SQL语句,不仅存在SQL注入风险,还不符合Access的日期语法要求——Access日期字面量需要用#包裹,而非单引号,且需保证日期格式为数据库可识别的标准格式。

最优方案:使用参数化查询

SQLAlchemy的text()支持参数绑定,能自动处理数据格式转换,同时规避注入风险,代码修改如下:

url = URL.create(
    drivername="access+pyodbc",
    query={"odbc_connect": connStr},
)
with create_engine(url).connect() as con:
    # 用占位符定义参数,避免直接拼接字符串
    sql_get_anag = text("""
        SELECT Tipo_Presenza FROM Presenza 
        WHERE ID_Anagrafica = :id_value 
          AND Giorno > :start_date 
          AND Giorno < :end_date
    """)
    # 通过params传入参数,SQLAlchemy自动适配Access格式
    Presenza_tab = pd.read_sql_query(
        sql_get_anag, 
        con, 
        params={
            "id_value": IDValue, 
            "start_date": current_day_insert, 
            "end_date": current_day_insert_1
        }
    )

关键细节说明

  1. 日期格式适配:确保current_day_insert和current_day_insert_1是Python的datetime对象,而非字符串。如果是字符串格式,先转换为datetime:
    from datetime import datetime
    current_day_insert = datetime.strptime(current_day_insert_str, "%d-%m-%y %H:%M:%S")
    current_day_insert_1 = datetime.strptime(current_day_insert_1_str, "%d-%m-%y %H:%M:%S")
    
  2. 为什么单引号没用:Access的日期语法要求用#(如#2024-05-24 00:00:00#),但手动拼接#仍有注入风险,参数化查询是最安全可靠的方式。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.22 16:04:57