Câu trả lời:
d = DateTime.now.utc
Giáo sư!
Điều đó dường như hoạt động trong Rails, nhưng không phải vani Ruby (và tất nhiên đó là những gì câu hỏi đang đặt ra)
d = Time.now.utc
Tuy nhiên, không hoạt động.
Có lý do gì bạn cần sử dụng DateTimevà không Time? Timenên bao gồm mọi thứ bạn cần:
irb(main):016:0> Time.now
=> Thu Apr 16 12:40:44 +0100 2009
DateTime.now.new_offset(0)
sẽ hoạt động trong Ruby tiêu chuẩn (tức là không có ActiveSupport).
new_offsetđối số phương thức mặc định là 0đã có. Vì vậy, DateTime.now.new_offsetcũng có thể được sử dụng.
Thật không may, lớp DateTime không có sẵn các phương thức tiện lợi trong lớp Time để thực hiện việc này. Bạn có thể chuyển đổi bất kỳ đối tượng DateTime nào thành UTC như sau:
d = DateTime.now
d.new_offset(Rational(0, 24))
Bạn có thể chuyển lại từ UTC sang localtime bằng cách sử dụng:
d.new_offset(DateTime.now.offset)
nơi dlà một đối tượng DateTime trong UTC thời gian. Nếu bạn muốn đây là các phương pháp tiện lợi, thì bạn có thể tạo chúng như sau:
class DateTime
def localtime
new_offset(DateTime.now.offset)
end
def utc
new_offset(Rational(0, 24))
end
end
Bạn có thể thấy điều này hoạt động trong phiên irb sau:
d = DateTime.now.new_offset(Rational(-4, 24))
=> #<DateTime: 106105391484260677/43200000000,-1/6,2299161>
1.8.7 :185 > d.to_s
=> "2012-08-03T15:42:48-04:00"
1.8.7 :186 > d.localtime.to_s
=> "2012-08-03T12:42:48-07:00"
1.8.7 :187 > d.utc.to_s
=> "2012-08-03T19:42:48+00:00"
Như bạn thấy ở trên, đối tượng DateTime ban đầu có độ lệch -04: 00 (Giờ miền Đông). Tôi đang ở Giờ Thái Bình Dương với chênh lệch -07: 00. Việc gọi localtimenhư được mô tả trước đó sẽ chuyển đổi đúng cách đối tượng DateTime thành giờ địa phương. Gọi utcđối tượng đúng cách sẽ chuyển đổi nó thành bù UTC.
Bạn có thể đặt ENV nếu bạn muốn Time.nowvà DateTime.nowphản hồi trong thời gian UTC.
require 'date'
Time.now #=> 2015-11-30 11:37:14 -0800
DateTime.now.to_s #=> "2015-11-30T11:37:25-08:00"
ENV['TZ'] = 'UTC'
Time.now #=> 2015-11-30 19:37:38 +0000
DateTime.now.to_s #=> "2015-11-30T19:37:36+00:00"
Trong irb:
>>d = DateTime.now
=> #<DateTime: 11783702280454271/4800000000,5/12,2299161>
>> "#{d.hour.to_i - d.zone.to_i}:#{d.min}:#{d.sec}"
=> "11:16:41"
sẽ chuyển đổi thời gian thành utc. Nhưng như đã đăng nếu đó chỉ là Thời gian bạn có thể sử dụng:
Time.now.utc
và lấy nó ngay lập tức.