Rails: convertir l'heure UTC en un autre fuseau horaire

Réponses:

206
time.in_time_zone(time_zone)

Exemple:

zone = ActiveSupport::TimeZone.new("Central Time (US & Canada)")
Time.now.in_time_zone(zone)

ou juste

Time.now.in_time_zone("Central Time (US & Canada)")

Vous pouvez trouver les noms des fuseaux horaires ActiveSupport en procédant comme suit:

ActiveSupport::TimeZone.all.map(&:name)
# or for just US
ActiveSupport::TimeZone.us_zones.map(&:name)
mckeed
la source
Dans irb, quand j'essaye Time.now.in_time_zone ('CST'), j'obtiens l'erreur "méthode indéfinie 'in_time_zone'". Y a-t-il des classes de rails dont j'ai besoin pour que cela fonctionne?
Drew Johnson
Quelle version de Rails utilisez-vous? Cela fonctionne-t-il si vous faites Time.zone.now.in_time_zone (...)?
mckeed
13
Pour utiliser ceci à l'extérieur des rails, d' require 'active_support/time'abord.
sunaku
3
Vous pouvez lister tous les fuseaux horaires en exécutant rake time:zones:all. Voir aussi rake -D time. Définissez le fuseau horaire par défaut dans config/application.rb.
user664833
1
@AdamEberlin Dans Rails, vous utilisez généralement ActiveSupport :: TimeWithZone, pas DateTime. Tout ce code fonctionne sur les objets Ruby DateTime ainsi que sur les objets Time.
mckeed
6

si Time.zonec'est votre fuseau horaire souhaité, vous pouvez utiliser@date.to_time.to_datetime

> @date
=> Tue, 02 Sep 2014 23:59:59 +0000
> @date.class
=> DateTime
> @date.to_time
=> 2014-09-02 12:59:59 -1100
> @date.to_time.to_datetime
=> Tue, 02 Sep 2014 12:59:59 -1100 
VladCovaliov
la source
Ne fonctionne pas sur Rails 5 `Time.zone # => Europe / Paris my_date # => mer, 29 mars 2017 19:00:20 +0200 my_date.to_time # =>" 2017-03-29T17: 00: 20.000+ 00:00 "my_date.to_time.to_datetime # => mer, 29 mars 2017 17:00:20 +0000`
Cyril Duchon-Doris
5

En rubis uni, avec seulement require 'date', utilisez la new_offsetméthode:

require 'date'

d=DateTime.parse('2000-01-01 12:00 +0200')
l=d.new_offset('-0700')
u=l.new_offset('UTC')
puts "#{u.strftime('%a %F %T %Z')} ❖ #{l.strftime('%a %F %T %Z')}"

Testé avec ruby ​​2.3.7 fourni en standard sur Mac OS X 10.13.

jbyler
la source
3

Essayez les objets TimeWithZone d' ActiveSupport manipulés avec TimeZone. ActiveSupport fournit également la méthode in_time_zone pour convertir une heure UTC en un fuseau horaire spécifié. La réponse de mckeed montre le code.

Fred
la source
Quelle est la syntaxe pour importer TimeWithZone dans ma classe? Ou est-ce que je l'obtiens par défaut avec Rails?
Drew Johnson
1
Je crois que vous l'obtenez par défaut. mckeed a le code dont vous avez besoin, mais vous ne le verrez pas dans irb. Vous devez l'exécuter dans Rails.
Fred
Vous avez raison - merci, Fred - il est livré avec Rails par défaut. J'attrapais des pailles, essayant de le faire fonctionner en irb.
Drew Johnson
3

Juste au cas où, si vous avez affaire à un objet ActiveRecord dans Rails.

Il peut être judicieux d'utiliser Time.use_zonepour un fuseau horaire par demande qui remplace le fuseau horaire par défaut défini dansconfig.time_zone

Plus de détails que j'explique à https://stackoverflow.com/a/25055692/542995

zdk
la source
0

J'utilise simple_form dans Rails 4 et je viens d'ajouter le champ de saisie comme

<%= f.input :time_zone, :as => :time_zone %>

avec la migration

class AddTimeZoneColumnToTextmessage < ActiveRecord::Migration
  def change
    add_column :textmessages, :time_zone, :string
  end
end
maudulus
la source
1
Cela ne répond pas à la question de savoir comment convertir les objets DateTime
zykadelic