timezone - sql server中从时区到时区的日期时间转换

标签 timezone sql-server-2012 unix-timestamp

我的数据库表中有一个 UNIX 时间戳列,它来自科威特时区的系统。

我的数据库服务器的时区是 Eastern Time US & Canada .现在我需要使用 SQL 查询将 UNIX 时间戳转换为科威特时区日期值。

谁能告诉我如何将此 UNIX 时间戳转换为科威特时区日期值?

最佳答案

Unix 时间戳是自 1970 年 1 月 1 日 UTC 以来的整数秒数。

假设您的意思是您的数据库中有一个带有此数字的整数列,那么您的数据库服务器的时区是无关紧要的。

首先将时间戳转换为 datetime类型:

SELECT DATEADD(second, yourTimeStamp, '1970-01-01')

这将是 UTC datetime对应于您的时间戳。

然后您需要知道如何将此值调整为您的目标时区。在世界上的大部分地区,由于夏令时,单个区域可以有多个偏移量。

不幸的是,SQL Server 无法直接处理工作时区。因此,例如,如果您使用美国太平洋时间,您将无法知道应该减去 7 小时还是 8 小时。其他数据库(Oracle、Postgres、MySql 等)有内置的方法来处理这个问题,但遗憾的是,SQL Server 没有。因此,如果您正在寻找通用解决方案,则需要执行以下操作之一:
  • 将时区数据导入表中,并在时区规则更改时维护该表。使用带有一堆自定义逻辑的表来解析特定日期的偏移量。
  • 使用 xp_regread获取包含时区数据的 Windows 注册表项,并再次使用一堆自定义逻辑来解析特定日期的偏移量。当然,xp_regread是一件坏事,需要授予某些权限,并且不受支持或文档。
  • 编写一个使用 TimeZoneInfo 的 SQLCLR 函数.Net 中的类。不幸的是,这个requires an "unsafe" SQLCLR assembly ,并可能导致不好的事情发生。

  • 恕我直言,这些方法都不是很好,并且没有直接在 SQL 中执行此操作的好的解决方案。最好的解决方案是将 UTC 值(原始整数或 UTC 中的 datetime)返回到您的调用应用程序代码,并在那里进行时区转换(例如,在 .Net 中使用 TimeZoneInfo 或其他平台中的类似机制)。

    但是 - 您很幸运,科威特(并且一直)处于夏令时不会改变的区域。一直是UTC+03:00。所以你可以简单地添加三个小时并返回结果:
    SELECT DATEADD(hour, 3, DATEADD(second, yourTimeStamp, '1970-01-01'))
    

    但请注意,这不是适用于任何时区的通用解决方案。

    如果需要,您可以返回其他 SQL 数据类型之一,例如 datetimeoffset ,但这只会帮助您反射(reflect)该值对于可能会查看它的人来说是三个小时的偏移量。它不会使转换过程有任何不同或更好。

    更新答案

    我创建了一个项目来支持 SQL Server 中的时区。您可以安装它from here .然后你可以像这样简单地转换:
    SELECT Tzdb.UtcToLocal('2015-07-01 00:00:00', 'Asia/Kuwait')
    

    您可以使用 any time zone from the IANA tz database ,包括使用夏令时的那些。

    您仍然可以使用我上面展示的方法从 unix 时间戳转换。将它们放在一起:
    SELECT Tzdb.UtcToLocal(DATEADD(second, yourTimeStamp, '1970-01-01'), 'Asia/Kuwait')
    

    再次更新

    在 SQL Server 2016 中,现在内置了对时区的支持 AT TIME ZONE 陈述。这在 Azure SQL 数据库 (v12) 中也可用。
    SELECT DATEADD(second, yourTimeStamp, '1970-01-01') AT TIME ZONE 'Arab Standard Time'
    

    More examples in this announcement.

    关于timezone - sql server中从时区到时区的日期时间转换,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16872007/

    相关文章:

    mysql - 从 PHP 将日期存储在 MySQL 中的最佳实践

    ios - 解析远程通知和时区

    c# - 为什么我不能将我的系统时间设置为接近夏令时转换的时间

    Java 将 unixtime 转换为日期,给出错误的结果

    sql - 如果使用 SUM 如何计算平均值

    使用变量和之间的 SQL 替代 IN 运算符

    sql - 如何在 SQL Server 中将 bigint(UNIX 时间戳)转换为日期时间?

    java - 写入 Oracle 时使用 java.util.Date 时区问题

    javascript - 在 JavaScript 中将一个时区转换为另一个时区

    xml - XML 包含多个命名空间 - 但它只有一个