操作数类型与参数化UPDATE查询类型冲突

时间:2017-05-10 01:34:23

标签: python sql sql-server python-2.7 pyodbc

我有一个带有以下列的SQL Server表(*表示允许NULL):

  • ID(int)
  • RequisitionID(int)
  • ApplicantID(int)
  • WorkflowStateID(int)
  • WorkflowDate(datetime)
  • SubmissionDate(datetime)
  • StartDate(date)*
  • DispositionID(int)*
  • ATSApplicationID(varchar(255))*
  • ApplicationLink(varchar(255))*
  • CreateDate(datetime)
  • ModifyDate(datetime)

我正在尝试使用带有Driver = SQL Server(MS SQL Server 2012数据库)的pypyodbc进行参数化INSERT查询。这是查询:

sql_statement = """
    UPDATE [hr].[ATS.Applications] SET RequisitionID = ?, WorkflowStateID = ?, WorkflowDate = ?, StartDate = ?, DispositionID = ?, ModifyDate = ? WHERE ID = ?
    """

cursor.execute(sql_statement,(new_application.requisition_id,
                              new_application.workflow_state,
                              new_application.workflow_date.strftime("%Y-%m-%dT%H:%M:%S"),
                              new_start_date,
                              new_application.disposition,
                              now,
                              old_application.ID))

cursor.commit()

导致以下错误:

DataError: (u'22018', u'[22018] [Microsoft][ODBC SQL Server Driver][SQL Server]Operand type clash: int is incompatible with date')

我假设其中一个日期字符串被解释为计算的整数,但是使用调试器,所有数据和数据都是数据类型似乎与我的表兼容:

new_application.requisition_id = {int} 7
new_application.workflow_state = {int} 19
new_application.workflow_date.strftime("%Y-%m-%dT%H:%M:%S") = {str} '2017-05-09T07:52:13'
new_start_date = {NoneType} None
new_application.disposition = {int} 7
now = {str} '2017-05-09T17:55:27'
old_application.ID = {int} 34402

我尝试将datetime值作为datetime对象和字符串插入,以及 似乎无法解决它所期望的数据类型。

为什么我对此UPDATE语句有疑问?

1 个答案:

答案 0 :(得分:1)

pypyodbc处理从Python date / datetime对象到相应SQL Server数据类型的类型转换,而不是依赖于字符串格式。

在下面的例子中,我假设:

  • new_application.workflow_date是Python日期时间对象
  • 来自原始问题的
  • now旨在使用datetime模块获取当前系统时间
sql_statement = """
UPDATE [hr].[ATS.Applications] SET RequisitionID = ?, WorkflowStateID = ?, WorkflowDate = ?, StartDate = ?, DispositionID = ?, ModifyDate = ? WHERE ID = ?
    """

cursor.execute(sql_statement,(new_application.requisition_id,
                              new_application.workflow_state,
                              new_application.workflow_date,
                              new_start_date,
                              new_application.disposition,
                              datetime.now(),
                              old_application.ID))

cursor.commit()

有关包含SQL Server DATETIME类型的支持示例,请参阅我的回答here