【问题标题】:How to deal with time storage in SQLSQL中如何处理时间存储
【发布时间】:2008-10-21 00:28:01
【问题描述】:

我有一个正在编写的 Web 应用程序(C#、MSSQL),当记录存储在系统中时,我需要存储时间戳。通常,我会使用 SQL 和 DATETIME 函数来执行此操作。但是,服务器位于与我们公司所在的不同时区......并且我们可能会更改为完全不同时区的另一台服务器。托管公司不会更改服务器时间以匹配我们当地的时区。 (不是我责怪他们,而是我尝试过的一件事。)

那么,我的问题是,存储记录更新的日期/时间的最佳方式是什么,以及在我们当地的时区将该日期/时间呈现给用户的最佳方式是什么?

我希望以最不混乱的方式执行此操作,因此只要解决方案易于实施,C# 和 SQL 的组合就可以了。 (我通常的风格是在存储过程中做更多的工作,而在 C# 中做更少的工作,如果这很重要的话。)

你能给我一些示例代码吗?谢谢!

【问题讨论】:

    标签: c# sql time


    【解决方案1】:

    始终将 DATETIME 数据存储在世界协调时间(UTC 又名 GMT)中

    • 这避免了所有时区问题
    • 这避免了夏令时问题
    • 这允许简单的日期数学始终有效
    • 这允许不同时区的交易保持同步
    • 这允许您将数据移动到不同时区的不同服务器,而不会搞砸一切
    • 等。 “通用”时间,有意义吗?

    C# DateTime 提供 DateTime.UtcNow 和 ToLocalTime(),SQL 提供 GETUTCDATE()。这是一个将 UTC 转换为本地时间的 SQL 函数 -

    -- convert UTC to local time
    create FUNCTION [dbo].[udfUtcToLocalTime]
    (
        @gmt datetime
    )
    RETURNS datetime
    AS
    BEGIN
        DECLARE @dt datetime
        SELECT 
            @dt = dateadd(millisecond,datediff(millisecond,getutcdate(), getdate()),@gmt)
        RETURN @dt
    END
    

    示例:

    SELECT dbo.udfUtcToLocalTime(someDateTimeField)
    FROM someTable
    

    【讨论】:

    • 当 timzeone 偏移量因夏令时发生变化时,此函数将失败。
    • @[Dave Markle]:应该会在夏令时更改时更改!
    • 他的意思是,如果您查看上周的信息,在日期更改之前,您会看到今天的偏移量而不是上周的偏移量。仅当您想根据今天的偏移量查看当地时间时,您的功能才有效。 .Net 函数 DateTime.ToLocalTime 不能以这种方式工作。它将根据该日期的偏移量向您显示当地时间。
    【解决方案2】:

    将 UTC 时间保存在您的数据库中,并在每次您想向用户展示它们时本地化这些时间

    【讨论】:

    • 在你的存储过程中使用 GETUTCDATE() 而不是 GETDATE() 如果不是从应用程序提供。
    【解决方案3】:

    将其存储为UTC时间,然后在客户端进行时区计算 在 C# 中使用 DateTime 对象上的 .ToUniversalTime() 来获取 UTC 时间,将其存储在服务器上,然后使用 .ToLocalTime() 将其转换回来。

    【讨论】:

    • 这与我所做的类似,只是我在 C# 中有自己的 ToLocalTime 扩展方法。那是因为网络服务器位于美国,但我希望时间显示为澳大利亚时间。
    猜你喜欢
    • 1970-01-01
    • 2010-09-10
    • 2018-08-02
    • 2012-06-29
    • 2015-05-06
    • 2011-03-29
    • 1970-01-01
    • 1970-01-01
    • 2011-01-22
    相关资源
    最近更新 更多