mad.ly rails, jquery, flash, etc    about »

We're looking for senior developer. More Info

Posted by
Geoff Buesing

Posted on
25 September 2008 @ 8pm

Tagged
rails, time zones

Making Rails time zone aware attributes and Chronic play well together

I came up with this monkeypatch to Time.zone.parse, so that it uses the Chronic time parsing library instead of Time.parse:

class ActiveSupport::TimeZone
  # requires technoweenie’s fork of the Chronic time parsing library
  # http://github.com/technoweenie/chronic/tree/master
  def parse(str)
    Chronic.time_class = self
    Chronic.parse(str, :now => now)
  end
end

…with this in place, I can assign natural language date/time strings to model attributes, and the values will be parsed in the current Time.zone:

>> e=Event.new(:starts_at => "last thursday at 5pm")
=> #<Event id: nil, title: nil, starts_at: "2008-09-18 22:00:00", created_at: nil, updated_at: nil>
>> e.starts_at
=> Thu, 18 Sep 2008 17:00:00 CDT -05:00

7 Comments

Posted by
Ed
25 October 2008 @ 5pm

I’m confused … where does this patch go?
Thanks.


Posted by
Geoff Buesing
27 October 2008 @ 7am

@Ed, the easiest thing to do is to put this code into a file (named time_zone_parse_with_chronic.rb, or whatever you like) in the config/initializers directory.


Posted by
Milton Macedo
1 November 2008 @ 1am

Keep up the good work! :)


Posted by
Mohegan111
1 November 2008 @ 4am

Hmm. Good post.


Posted by
Jeff Judge
2 November 2008 @ 2pm

Geof,

I just found your blog. Thanks for all the helpful timezone info.

Related to this post, I’m curious how you do you handle certain parsing issues with Chhronic. In an application that I work on, I added some logic similar to this:

t = Chronic.parse(str)
if t.nil?
t = Time.parse(str)
end

That logic isn’t great because Chronic doesn’t know how to parse strings like “11/02/2008 01:20 PM” (it returns nil), yet Time.parse defaults to Time.now when parsing strings like “asdf” (which the ruby core team says is on purpose: http://redmine.ruby-lang.org/issues/show/281). It seems like Chronic.parse should be able to handle it all. I thought you might have run into some of this before.


Posted by
samuells
5 November 2008 @ 10am

Thanks for the post, I have been having the same problems.


Posted by
Geoff Buesing
8 November 2008 @ 11am

@Jeff –

1. Time.parse treating unknown strings as Time.now is annoying and, imo, useless behavior — which is why I made Rails’ Time.zone.parse just return nil when it doesn’t understand input.

2. looks like Chronic fails to recognize “11/02/2008 01:20 PM” because of the leading zero on the hour — the existence of such cases is probably a good argument for layering Chronic parsing on top of TimeZone#parse via alias_method_chain, versus re-implementing it.


Leave a Comment