Trilhos ActiveSupport Tempo de análise?

votos
30

módulo ActiveSupport carris estende a classe rubi Tempo embutido com um número de métodos.

Notavelmente, há o to_formatted_smétodo, que permite que você escreva Time.now.to_formatted_s(:db)para obter uma string no formato de banco de dados, em vez de ter que escrever feias strftimeformato-cordas em todos os lugares.

A minha pergunta é, existe uma maneira de ir para trás?

Algo como Time.parse_formatted_s(:db)o que analisar uma cadeia em formato de banco de dados, retornando um novo objeto Time. Este parece ser algo que rails deve fornecer, mas se for, eu não posso encontrá-lo.

Sou apenas não são capazes de encontrá-lo, ou eu preciso escrevê-lo eu mesmo?

obrigado

Publicado 10/12/2008 em 00:52
fonte usuário
Em outras línguas...                            


5 respostas

votos
55

Parece que ActiveSupport fornece os métodos de análise que você está procurando (e eu estava procurando também), depois de tudo! - pelo menos se a cadeia que está tentando analisar é um padrão, ISO-8601-formatado ( :dbformato) data.

Se a data que você está tentando analisar já está em seu fuso horário local, é realmente fácil!

 > Time.zone.parse('2009-09-24 08:28:43')
=> Thu, 24 Sep 2009 08:28:43 PDT -07:00

 > Time.zone.parse('2009-09-24 08:28:43').class
=> ActiveSupport::TimeWithZone

e que o tempo-time-zone consciente pode então ser facilmente convertido para UTC

 > Time.zone.parse('2009-09-24 08:28:43').utc
=> 2009-09-24 15:28:43 UTC

ou para outros fusos horários:

 > ActiveSupport::TimeZone.us_zones.map(&:name)
=> ["Hawaii", "Alaska", "Pacific Time (US & Canada)", "Arizona", "Mountain Time (US & Canada)", "Central Time (US & Canada)", "Eastern Time (US & Canada)", "Indiana (East)"]

 > Time.zone.parse('2009-09-24 08:28:43').utc.in_time_zone('Eastern Time (US & Canada)')
=> Thu, 24 Sep 2009 11:28:43 EDT -04:00

Se a seqüência de data que você está tentando analisar está em UTC, por outro lado, não parece que haja qualquer método para analisá-lo diretamente em um TimeWithZone, mas eu era capaz de contornar que ser o primeiro a utilizar DateTime.strptime ...

Se a data que você está tentando analisar está em UTC e você quer que ele fique como UTC, você pode usar:

 > DateTime.strptime('2009-09-24 08:28:43', '%Y-%m-%d %H:%M:%S').to_time
=> 2009-09-24 08:28:43 UTC

Se a data que você está tentando analisar está em UTC e quer que ele convertido para o seu fuso horário padrão, você pode usar:

 > DateTime.strptime('2009-09-24 08:28:43', '%Y-%m-%d %H:%M:%S').to_time.in_time_zone
=> Thu, 24 Sep 2009 01:28:43 PDT -07:00

Parece que ele ainda pode analisar outros formatos, tais como o formato estranho que Tempo # to_s produz:

irb -> Time.zone.parse('Wed, 23 Sep 2009 02:18:08').to_s(:db)
    => "2009-09-23 09:18:08"

irb -> Time.zone.parse('Wed, 23 Sep 2009 02:18:08 EDT').to_s(:db)
    => "2009-09-23 06:18:08"

Estou muito impressionado.

Aqui estão mais alguns exemplos de [ http://api.rubyonrails.org/classes/ActiveSupport/TimeWithZone.html][1] :

  Time.zone = 'Eastern Time (US & Canada)'        # => 'Eastern Time (US & Canada)'
  Time.zone.local(2007, 2, 10, 15, 30, 45)        # => Sat, 10 Feb 2007 15:30:45 EST -05:00
  Time.zone.parse('2007-02-10 15:30:45')          # => Sat, 10 Feb 2007 15:30:45 EST -05:00
  Time.zone.at(1170361845)                        # => Sat, 10 Feb 2007 15:30:45 EST -05:00
  Time.zone.now                                   # => Sun, 18 May 2008 13:07:55 EDT -04:00
  Time.utc(2007, 2, 10, 20, 30, 45).in_time_zone  # => Sat, 10 Feb 2007 15:30:45 EST -05:00

Mais documentação liga para referência:

Respondeu 24/09/2009 em 22:24
fonte usuário

votos
5
ActiveSupport::TimeZone.new('UTC').parse('2009-09-23 09:18:08')
=> Wed, 23 Sep 2009 09:18:08 UTC +00:00
Respondeu 05/08/2010 em 17:17
fonte usuário

votos
3

Trilhos 5 finalmente fornece strptime!

value = '1999-12-31 14:00:00'
format = '%Y-%m-%d %H:%M:%S'
Time.zone.strptime(value, format)
# => Fri, 31 Dec 1999 14:00:00 HST -10:00

ActiveSupport::TimeZone.all.sample.strptime(value, format)
# => Fri, 31 Dec 1999 14:00:00 GST +04:00
Respondeu 07/02/2016 em 06:36
fonte usuário

votos
2

Eu apenas corri para este tão bem e nenhuma das respostas acima foram satisfatórios para mim. Idealmente pode-se usar ActiveSupport::TimeZonecomo Timee chamar .strptimesobre ele com qualquer formato arbitrário e receber de volta o correto TimeZoneobjeto. ActiveSupport::TimeZone.strptimenão existe por isso criei este monkeypatch:

 class ActiveSupport::TimeZone
    def strptime(str, fmt, now = self.now)
      date_parts = Date._strptime(str, fmt)
      return if date_parts.blank?
      time = Time.strptime(str, fmt, now) rescue DateTime.strptime(str, fmt, now)
      if date_parts[:offset].nil?
        ActiveSupport::TimeWithZone.new(nil, self, time)
      else
        time.in_time_zone(self)
      end
    end
  end
Respondeu 17/05/2012 em 23:37
fonte usuário

votos
1
>> "2009-09-24".to_date
=> Thu, 24 Sep 2009
>> "9/24/2009".to_date
=> Thu, 24 Sep 2009

Funciona muito bem, a menos que a sua data é em algum formato estranho.

Respondeu 25/09/2009 em 02:40
fonte usuário

Cookies help us deliver our services. By using our services, you agree to our use of cookies. Learn more