dbFailOnError仅限时间值的SQL Server日期时间错误



我在SQL Server中有一个带日期时间列的链接表,我在其中存储一个仅限时间的值*。如果我在没有dbFailOnError的情况下执行UPDATE查询,它会将该命令转换为SELECT,然后是每次执行一行的单个UPDATE语句:

exec sp_executesql N'UPDATE "dbo"."Appeals" SET "HearingTime"=@P1 
                     WHERE "AppealID" = @P2'
                  ,N'@P1 datetime,@P2 int','1899-12-30 09:00:00',1
...
exec sp_executesql N'UPDATE "dbo"."Appeals" SET "HearingTime"=@P1 
                     WHERE "AppealID" = @P2'
                  ,N'@P1 datetime,@P2 int','1899-12-30 09:00:00',4

如果我执行完全相同的UPDATE查询,但使用dbFailOnError,我会得到以下翻译:

UPDATE "dbo"."Appeals" SET HearingTime={t '09:00:00'} 

有趣的是,dbFailOnError在后端强制执行更高效的UPDATE,但我真正关心的是时间值本身。

在第一个示例中,Access正确地将日期时间设置为12/30/1899(MS Access神奇的"零"日(。在第二种情况下,这种情况不会发生。最终的结果是,第一个例子"有效",而第二个则不然。

我的意思是,如果我在数据表视图中查看HearingTime字段,Access会将第一个显示为:

9:00:00 AM

第二个显示为(截至本文撰写之时,9/13/16是今天的日期(:

9/3/2016 9:00:00 AM

我不得不假设这是微软的一个错误。还是我在这里错过了什么?我有比报告错误并希望微软有一天能修复它更好的选择吗?


*是的,我知道SQL Server中存在time数据类型。它与MS Access日期时间类型不兼容,所以在MS Access链接表中对我来说用处不大。

我能够使用带有Access SQL日期/时间文字的查询来重现您的问题。两个

Dim cdb As DAO.Database
Set cdb = CurrentDb
cdb.Execute "UPDATE dbo_Appeals SET HearingTime=#10:00:00#", dbFailOnError

Dim cdb As DAO.Database
Set cdb = CurrentDb
cdb.Execute "UPDATE dbo_Appeals SET HearingTime=#1899-12-30 11:00:00#", dbFailOnError

导致[HearningTime]值为当前日期(2016-09-03(,而不是"零"日期。

然而,将完整的日期/时间作为字符串传递似乎适用于

Dim cdb As DAO.Database
Set cdb = CurrentDb
cdb.Execute "UPDATE dbo_Appeals SET HearingTime='1899-12-30 12:00:00'", dbFailOnError

(省略字符串值中的日期部分会导致[HearningTime]值的SQL Server DATETIME"零"日期为1900-01-01。(

而且,更好的是,带有DAO.QueryDef对象的参数化查询似乎也能正确工作

Dim cdb As DAO.Database
Set cdb = CurrentDb
Dim qdf As DAO.QueryDef
Set qdf = cdb.CreateQueryDef("", _
        "PARAMETERS prmHearingTime DateTime;" & _
        "UPDATE dbo_Appeals SET HearingTime=[prmHearingTime]")
qdf!prmHearingTime = #10:00:00 AM#
qdf.Execute dbFailOnError

这是一个很好的问题,我可以重现它。

这似乎是ODBC驱动程序中的一个错误,因为您演示的行为是SQL Server的行为,ODBC驱动程序应该对此进行补偿,就像您在第一个示例中所做的那样,它提供了完整的日期时间字符串,当在Access中读回时,该字符串将正确转换。

除了在读回数据时将TimeValue应用于日期-时间值之外,我看不出其他解决方法。然而,这将停止使用时间字段的索引。

SQL Server的数据类型Time不能用于许多事情,因为ODBC驱动程序将这些数据作为文本读取。

相关内容

  • 没有找到相关文章

最新更新