在Rails中将时间从一个时区转换为另一个时区

我的created_at时间戳存储在UTC:

 >> Annotation.last.created_at => Sat, 29 Aug 2009 23:30:09 UTC +00:00 

如何将其中一个转换为“东部时间(美国和加拿大)”(考虑到夏令时)? 就像是:

 Annotation.last.created_at.in_eastern_time 

使用DateTime类的in_time_zone方法

 Loading development environment (Rails 2.3.2) >> now = DateTime.now.utc => Sun, 06 Sep 2009 22:27:45 +0000 >> now.in_time_zone('Eastern Time (US & Canada)') => Sun, 06 Sep 2009 18:27:45 EDT -04:00 >> quit 

所以对于你的特定例子

 Annotation.last.created_at.in_time_zone('Eastern Time (US & Canada)') 

虽然这是个老问题,但值得一提的是, 在之前的回复中 ,build议使用before_filter来临时设置时区。

永远不应该这样做,因为Time.zone将信息存储在线程中,并且可能会泄露给该线程处理的下一个请求。

相反,您应该使用around_filter来确保在请求完成后Time.zone被重置。 就像是:

 around_filter :set_time_zone private def set_time_zone old_time_zone = Time.zone Time.zone = current_user.time_zone if logged_in? yield ensure Time.zone = old_time_zone end 

阅读更多关于这里

如果你添加到你的/config/application.rb

 config.time_zone = 'Eastern Time (US & Canada)' 

那么你可以细胞

 Annotation.last.created_at.in_time_zone 

在指定的时区获得时间。

将您的时区设置为东部时间。

您可以在config / environment.rb中设置您的默认时区

 config.time_zone = "Eastern Time (US & Canada)" 

现在所有logging都将在该时区。 如果你需要不同的时区,比如基于用户时区,你可以在你的控制器中用before_filter来改变它。

 class ApplicationController < ActionController::Base before_filter :set_timezone def set_timezone Time.zone = current_user.time_zone end end 

只要确保你所有的时间都存储在数据库中的UTC,一切都会很好。

如果你configuration你的/config/application.rb

 config.time_zone = 'Eastern Time (US & Canada)' Time.now.in_time_zone DateTime.now.in_time_zone