如何批量转换DATETIME条目的时区?

问题描述 投票:0回答:1

在过去的一年半左右的时间里,我们的数据库服务器一直在使用东部时间,而DATETIME类型几乎是唯一使用的,所以我们数据库中的日期时间一直是不受时区影响的,因为只存储了时间戳。我已经在应用程序中添加了一些代码,以便能够将时间转换为当地时区,以期待改变这种情况。

我知道最好的做法是始终使用UTC,现在我想 "切入 "到UTC。我想知道有什么简单的方法可以将所有数据库中的DATETIMEs从东方时间改为UTC。我的意思是,从字面上看,修改每条记录的任何DATETIME属性,因为改变服务器上的时区不会调整这些。有没有一个命令可以轻松做到这一点?

我一直在寻找一些使用convert的例子,但是这些例子似乎只是在飞行中做这些事情--而不是实际修改数据库中的数据。我正在寻找类似的东西。

UPDATE [all tables] SET [all DATETIME attributes] = [current server/DB time (Eastern Time) -> UTC]

(然后,我希望能把服务器时间改成UTC,没人会注意到发生了什么)

但是,更糟糕的是,在过去的一年半里,夏令时已经过去了好几次,所以在每个日期时间上加5个小时的简单方法也行不通。有没有一个简单的办法来解决这个烂摊子?会不会 CONVERT_TZ 足够了,还是会把事情搞得一团糟?

mysql mariadb
1个回答
2
投票

好了,这个过程不一定复杂,但也不像大家希望的那么明显,所以我发个答案。这是我的工作方法。

  1. 检查是否 SELECT CONVERT_TZ(now(),'US/Eastern','US/Central'); 无所不能

首先,要确保上面的命令不会回到 NULL 当你执行它时。如果它确实返回 NULL就像我一样,完成下面的步骤1到4。

  1. cd到 /usr/bin
  2. ./mysql_tzinfo_to_sql /usr/share/zoneinfo | ./mysql -u root -p --database=mysql
  3. 输入密码
  4. 运转 service mariadb restart (或适当的命令)来重新启动DB服务。
  5. 运行 SELECT CONVERT_TZ(now(),'US/Eastern','US/Central'); - 现在 现在应该可以了 (不返回 NULL)

  6. 运转 sudo timedatectl set-timezone Etc/UTC

现在运行 SET GLOBAL time_zone = 'Etc/UTC';

现在,服务器时间和数据库时间都是UTC。

现在,我们必须在数据库中手动更新所有合适的列到UTC。

对于每个适用的表和列组合,运行类似这样的程序。

 UPDATE table SET `datetime` = CONVERT_TZ(`datetime`, 'America/New_York','Etc/UTC');

现在,数据库的时间已经更新了,所有的记录也都更新为UTC。

唯一需要注意的是,你可能要注意那些在更新表的同时被添加的记录。理想的情况是,你会把所有这些都准备成一个批处理的SQL语句,在改变服务器时间后立即执行,这样就不会有任何闪失。

最后,在最后,运行 service apache2 restart 来重新启动Web服务器。本例中的DB位于Web服务器上,由于某种原因,在重启Apache之前,时间没有调整好。


0
投票

思考一下完整的问题。

当你把一个时间 "08:00 "存储到一个 DATETIME. 世界各地的每个人都会 SELECT 即 "08:00"。

当你把 "08:00 "的时间存储到一个。TIMESTAMP...

  1. 它是根据你所在的时区转换的 INSERTing 到UTC。
  2. 有人在做 SELECT 会根据读者的时区重新转换。 所以他可能不会看到 "08:00"。

这些操作中的每一个对某些应用来说都是 "正确的",但对其他应用来说就不是了。

大约有5种模式;MySQLMariaDB只提供这两种模式。

你可以用笨拙的代码,分别跟踪时区,并在需要的地方进行调整。 但是,首先,看看是否正确配置和使用了 TIMESTAMP 会更简单。

还请注意 DATETIME 一年两次搞砸了(如果你所在的地区使用 "夏令时 "的话)--每年多一个小时,少一个小时。

© www.soinside.com 2019 - 2024. All rights reserved.