Azure SQL 显示本地时间

vac*_*cip 1 t-sql sql-server timezone azure-sql-database

我正在尝试以本地时间显示日期时间值。默认情况下,Azure SQL 数据库以 UTC 存储日期和时间,没有办法解决这个问题。(从内部部署的 SQL Server 迁移时这很痛苦。)我想以中欧时间显示存储的时间值。

现在当地时间是 11:30 (CET)。UTC 时间是 10:30。

DECLARE @TestTime DATETIME;
SET @TestTime = '2016-11-02 10:30:00'

SELECT @TestTime
--Returns 2016-11-02 10:30:00
SELECT @TestTime AT TIME ZONE 'Central European Standard Time'
--Returns 02 November 2016 10:30:00 +01:00
Run Code Online (Sandbox Code Playgroud)

我需要以某种方式返回 2016-11-02 11:30:00。现在是有趣的部分:

正如这里所建议的:

SELECT convert(DATETIME,@TestTime AT TIME ZONE 'Central European Standard Time',1)
--Returns 2016-11-02 09:30:00 So instead of adding the timezonedifference it subtracts it.
Run Code Online (Sandbox Code Playgroud)

这有效,但让我恶心:

SELECT DATEADD(MINUTE,DATEPART(tz,@TestTime AT TIME ZONE 'Central European Standard Time'),@TestTime)
--Returns 2016-11-02 11:30:00
Run Code Online (Sandbox Code Playgroud)

这里建议一个类似的解决方案,但它使用字符串操作。我怀疑 AT TIME ZONE 有问题;它应该显示 11:30 +1,而不是 10:30 +1,不是吗?

真的没有正确的方法可以在当地时间显示 UTC 时间吗?这种“绕过它”感觉非常肮脏,尤其是因为在任何时候它都可能停止工作(例如,Microsoft 修复/引入了一个错误)。

谢谢!

Mat*_*int 5

AT TIME ZONE语句执行两个不同的操作:

  1. 断言,一个datetime(或datetime2)是在特定的时间段,从而查找正确的该区域并返回一个偏移datetimeoffset为正确的值的偏移施加。

  2. 要将值转换datetimeoffset不同的时区,请使用与源值的偏移量来确定确切的时间点,然后查找所请求时区的新偏移量并应用它。这将返回一个datetimeoffset可能与原始本地时间和偏移量不同的本地时间和偏移量,但代表相同的时刻。

您仅使用第一部分。要转换datetime从UTC到一个特定的时间段,你需要使用两个

SELECT @TestTime AT TIME ZONE 'UTC' AT TIME ZONE 'Central European Standard Time'
Run Code Online (Sandbox Code Playgroud)

所述第一AT TIME ZONE断言,输入datetime是在UTC,导致datetimeoffset具有+00:00用于偏移。第二个AT TIME ZONE将其转换为请求的时区。