ISO8601 is a standard for representing date/time information as a string. ISO8601 dates look like this: 2009-10-26T04:47:09Z
.
There are a lot of good reasons to store dates in the ISO8601 format. The format is…
- Unambiguous. There is never any question how to interpret them.
- Human-readable. You can look at dates stored in ISO8601 and interpret them easily.
- Widely-supported. All major programming languages have libraries for parsing and writing ISO8601 dates.
- Sortable. If you follow a few simple rules, ISO8601 dates sort lexicographically into the order you would expect.
That last property makes ISO8601 a particularly good candidate for date/time storage in simple non-relational data stores like Amazon’s SimpleDB. Storing dates as ISO8601 lets you sort records by date in data stores which don’t support a native date/time data type – without sacrificing human-readability.
Using ISO8601 from Ruby couldn’t be simpler, if you know where to look for the tools. If you look at the Ruby Time
class by itself, you won’t find any reference to ISO8601. The secret is to require the ‘time’ library:
irb(main):001:0> time = Time.now.utc.iso8601 NoMethodError: undefined method `iso8601' for Mon Oct 26 04:46:57 UTC 2009:Time from (irb):1 from :0 irb(main):002:0> require 'time' => true irb(main):003:0> time = Time.now.utc.iso8601 => "2009-10-26T04:47:09Z" irb(main):004:0> Time.iso8601(time) => Mon Oct 26 04:47:09 UTC 2009
Note the use of utc
to convert the local time into universal time (aka Greenwich Mean). This is important if you want your time strings to be lexicographically sortable. The “Z” on the end of the ISO8601 date indicates that it is in UTC, not a local time zone.
require 'rss' works because it is requiring 'time'.
If you just want the iso8601 support, you can go with: require 'time'
Also, Time#iso8601 takes a handy optional argument for the number of fractional digits at the end.
I've had to use this to interact with brittle external services, for example.
Thanks, I've updated the post!
require 'rss' works because it is requiring 'time'.
If you just want the iso8601 support, you can go with: require 'time'
Also, Time#iso8601 takes a handy optional argument for the number of fractional digits at the end.
I've had to use this to interact with brittle external services, for example.
Thanks, I've updated the post!
What is about time periods ? How can I get format like this PT1H30M ?
The ruby ‘time’ library only handles the xmlschema time discussed. I’m unaware of implementations of the full iso8601 spec. Perhaps one of the microformats tools uses it. see http://microformats.org/wiki/datetime-design-pattern
There is a gem that provides some support for this.
gem listing: http://rubygems.org/gems/iso8601
source: https://github.com/arnau/ISO8601
Here’s a small session using it:
Great post regarding iso8601. I was trying to load a Time object from a YAML config file and everything else I did just returned a string representation of the date. By using the iso8601 format, YAML correctly parses it back to a Time object. 🙂
Also, the instance method Date#strftime() returns the ISO-8601 representation of the object. You can give it a formatting string as a parameter to yield the date it represents in other formats.