【发布时间】:2020-07-25 15:02:34
【问题描述】:
我的环境是:
- Ruby 2.6.3p62(2019-04-16 修订版 67580)[x86_64-darwin18]
- Rails 6.0.2.1
- MacOS X Mojave
- psql
- Puma 版本 4.3.3 (Ruby 2.6.3-p62)
出于某种原因,Rails 在我的数据库中将DateTime.now 保存为未来 7 小时:
2.6.3 :002 > DateTime.now
=> Sun, 12 Apr 2020 20:52:00 -0700
2.6.3 :003 > v.last_prompting = DateTime.now
=> Sun, 12 Apr 2020 20:52:05 -0700
2.6.3 :004 > v.save
(0.1ms) begin transaction
Volunteer Update (0.3ms) UPDATE "volunteers" SET "updated_at" = ?, "last_prompting" = ? WHERE "volunteers"."id" = ? [["updated_at", "2020-04-13 03:52:10.964288"], ["last_prompting", "2020-04-13 03:52:05.779767"], ["id", 1]]
(1.1ms) commit transaction
=> true
2.6.3 :005 > v.last_prompting
=> Sun, 12 Apr 2020 20:52:05 PDT -07:00
看看last_prompting 和updated_at - 都在 4 月 13 日,今天是 4 月 12 日。
但是当我检查控制台中的时间时,它做了正确的事情:
2.6.3 :005 > v.last_prompting
=> Sun, 12 Apr 2020 20:52:05 PDT -07:00
2.6.3 :006 > v.last_prompting.future?
=> false
2.6.3 :007 > v.last_prompting.past?
=> true
我正在尝试编写一个方法来表达last_prompting 是多久以前的:
def prompting_age
return "never" if self.last_prompting == nil
if self.last_prompting.between?(Time.now - 720.minutes, Time.now - 10.years)
">12 hrs"
elsif self.last_prompting.between?(Time.now - 240.minutes, Time.now - 719.minutes)
">4 hrs"
elsif self.last_prompting.between?(Time.now - 61.minutes, Time.now - 239.minutes)
">1 hr"
elsif self.last_prompting.between?(Time.now, Time.now - 60.minutes)
"<1 hr"
else
"weird"
end
end
每次我测试这个方法时,它都会返回“奇怪”。我认为这是因为 Rails 给出了未来的日期,但是当我通过 Puma 运行应用程序时它不会在控制台中这样做。
【问题讨论】:
-
我们无法确定问题出在哪里,因为您没有告诉我们有关您的数据库架构的任何信息,但它闻起来像是时区不匹配。您的控制台知道您的计算机所在的时区,但数据库没有任何线索,可能正在使用 UTC。这可能导致这种不匹配。您可以告诉数据库要使用哪个时区,或者,可能更聪明的是,在存储之前将 DateTime 和 Time 值转换为 UTC。另外,您使用的是
psql还是PostgreSQL?psql是 CLI 客户端,PostgreSQL 是 DBM;它们是不同的,不要混淆。 -
Time.zone.now.in_time_zone('Etc/UTC')会解决它。
标签: ruby-on-rails ruby postgresql datetime