date-formatter gem - date formatter by example; auto-builds the strftime format string from an example date

Hello,

   I've put together a new date formatter gem / library [1] that lets you
format dates e.g. "January 02, 2006"
using an example as a format string e.g "January 02, 2006"
instead of the classic strftime format specifier e.g. "%B %d, %Y". The
date by example adds:

- String#to_strfime
- Date#format
- Time#format
- DateTime#format
- NilClass#format

to the built-in classes.

Example - The new `String#to_strftime` method auto-builds the
`strftime` format string from an example date:

require 'date/formatter'

p 'January 02, 2006'.to_strftime          #=> "%B %d, %Y"
p 'Mon, Jan 02'.to_strftime               #=> "%a, %b %d"
p '2 Jan 2006'.to_strftime                #=> "%-d %b %Y"
p 'Monday, January 2, 2006'.to_strftime   #=> "%A, %B %-d, %Y"

p 'Mon, Jan 02 3:00'.to_strftime          #=> "%a, %b %d %-H:%M"
p '2 Mon 2006 03:00'.to_strftime          #=> "%-d %b %Y %H:%M"

Example - The new `Date#format` method formats the date like the
passed in example:

date = Date.today   ## test run on 2020-02-09

p date.format( 'January 02, 2006' )         #=> "February 09, 2020"
p date.format( 'Mon, Jan 02' )              #=> "Sun, Feb 09"
p date.format( '2 Jan 2006' )               #=> "9 Feb 2020"
p date.format( 'Monday, January 2, 2006' )  #=> "Sunday, February 9, 2020"

and so on. Happy date and time formatting with ruby. Cheers. Prost.

[1] https://github.com/feedreader/pluto/tree/master/date-formatter

Thanks for this! There was a gem named (IIRC) stamp that had this same signature. I recall using it about 8 years ago. So much more friendly than the % marked template strings, although unless you picked your numbers carefully, easy to get mixed up between US and REST_OF_THE_WORLD three-number formatting. 4-3-20 could mean March or April, if you see what I mean.

Walter

···

On Feb 17, 2020, at 8:57 AM, Gerald Bauer <gerald.bauer@gmail.com> wrote:

Hello,

  I've put together a new date formatter gem / library [1] that lets you
format dates e.g. "January 02, 2006"
using an example as a format string e.g "January 02, 2006"
instead of the classic strftime format specifier e.g. "%B %d, %Y". The
date by example adds:

- String#to_strfime
- Date#format
- Time#format
- DateTime#format
- NilClass#format

to the built-in classes.

Example - The new `String#to_strftime` method auto-builds the
`strftime` format string from an example date:

require 'date/formatter'

p 'January 02, 2006'.to_strftime          #=> "%B %d, %Y"
p 'Mon, Jan 02'.to_strftime               #=> "%a, %b %d"
p '2 Jan 2006'.to_strftime                #=> "%-d %b %Y"
p 'Monday, January 2, 2006'.to_strftime   #=> "%A, %B %-d, %Y"

p 'Mon, Jan 02 3:00'.to_strftime          #=> "%a, %b %d %-H:%M"
p '2 Mon 2006 03:00'.to_strftime          #=> "%-d %b %Y %H:%M"

Example - The new `Date#format` method formats the date like the
passed in example:

date = Date.today   ## test run on 2020-02-09

p date.format( 'January 02, 2006' )         #=> "February 09, 2020"
p date.format( 'Mon, Jan 02' )              #=> "Sun, Feb 09"
p date.format( '2 Jan 2006' )               #=> "9 Feb 2020"
p date.format( 'Monday, January 2, 2006' )  #=> "Sunday, February 9, 2020"

and so on. Happy date and time formatting with ruby. Cheers. Prost.

[1] https://github.com/feedreader/pluto/tree/master/date-formatter

Unsubscribe: <mailto:ruby-talk-request@ruby-lang.org?subject=unsubscribe>
<http://lists.ruby-lang.org/cgi-bin/mailman/options/ruby-talk>

Hello,

    Thanks for your kind words. In the new date-formatter a
"free-standing" number is always a day number (e.g. 3:00 or 03:00 is
interpreted as time, that is, hours and minutes).

  If you want a format like 4-3-20 than you have to use the "symbol"
format shortcuts
  e.g.
     "D-M-YY".to_strftime
     "M-D-YY.to_strftime
     "DD-MM-YY".to_strftime # zero-padded day and month
     "DMYY".to_strftime # works too
     or with time
      "hmmss".to_strftime
     and so on.

    Cheers. Prost.

PS: Still kind of undecided if it is worth to reserve 1, 01, etc. for
months and 2, 02, etc. for days and 3, 03, etc. for hours and 4, 04,
for minutes and 5, 05, etc. for seconds and so on. For now you can
write:

Time.now.format("Friday, February 4, 2020")

and it works too in Ruby's date formatter (but NOT using Golang's time
format). In Golang you always MUST use the Monday, January 2, 2006
15:04:05 -7:00 reference date that you can supposedly learn and keep
in memory by using the 0-1-2-3-4-5-6-7 trick. 0 = Monday, 1 = January,
2 = Day 2, 3 = Hour 15, 4 = Minute 4, 5 = Second 5, 6 = Year 2006, 7 =
Timezone -7:00 (MST). Anyone has any opinions on the Go Lang Reference
Date Style? Pro or contra?

In Golang you always MUST use the Monday, January 2, 2006
15:04:05 -7:00 reference date that you can supposedly learn and keep
in memory by using the 0-1-2-3-4-5-6-7 trick. 0 = Monday, 1 = January,
2 = Day 2, 3 = Hour 15, 4 = Minute 4, 5 = Second 5, 6 = Year 2006, 7 =
Timezone -7:00 (MST). Anyone has any opinions on the Go Lang Reference
Date Style? Pro or contra?

I always found Golang's way to specify date formatting highly confusing. All other languages I work with use placeholders, and placeholders are what one is used to with printf() and similar functions. Golang breaks consistency here in my opinion. When I first read Golang's docs about the topic, I had a hard time to understand what they want from me. Not using placeholders came over as completely arcane and entirely unusual.

Since I have no real intention to memoise Golang's release year (2006, appearently), I always need to pull up the reference documentation to get the correct date. The most important strftime placeholders are easy to learn, because they map to the first letter of the English name for the component, but even in case I forget them, I can fire up the strftime(3) manpage much faster than I can browse to golang.org's reference docs.

To me, it appears as if Golang solved a problem here that never existed.

···

--
Blog: https://mg.guelker.eu

Hello,
   Thanks for the contrarian - or maybe yours is the mainstream :slight_smile:
opinion. For the record, 2006 is NOT the Go birthday year - it's 2009
according to Wikipedia [1]. It's just a "menomic device", that is,
2006 fits into the 0-1-2-3-4-5-6-7 series.
   Cheers. Prost.

PS: One upside of the Go lang style is that it's unambiguous and also
easy to code up.
Here's all the ruby code from the date_by_example gem [2]:

class GoStyleDateByExampleFormatter
  attr_accessor :reference

  def initialize(reference)
    @reference = reference
    @format_string = nil
  end

  FORMATS = {
    ".000000000" => ".9N",
    "-07:00:00" => "%::z",
    ".000000" => ".%6N",
    "January" => "%B",
    "JANUARY" => "%^B",
    "Monday" => "%A",
    "MONDAY" => "%^A",
    "-07:00" => "%:z",
    "-7000" => "%z",
    "2006" => "%Y",
    ".000" => ".%L",
    "002" => "%j",
    "Jan" => "%b",
    "JAN" => "%^b",
    "Mon" => "%a",
    "MON" => "%^a",
    "MST" => "%Z",
    "15" => "%H",
    "06" => "%y",
    "01" => "%m",
    "02" => "%d",
    "03" => "%I",
    "PM" => "%p",
    "pm" => "%P",
    "04" => "%M",
    "05" => "%S",
    "1" => "%-m",
    "2" => "%-e",
    "3" => "%l"}.freeze

  FORMAT_MATCHER = Regexp.union(FORMATS.keys)

  def format_string
    @format_string ||= reference.gsub(FORMAT_MATCHER, FORMATS)
  end

  def format(date)
    date.strftime(format_string)
  end
end

[1]: https://en.wikipedia.org/wiki/Go_(programming_language)
[2] https://github.com/noelrappin/date_by_example/blob/master/lib/date_by_example/example_formatter.rb

···

El lun., 17 feb. 2020 a las 18:19, Marvin Gülker (<post+rubytalk@guelker.eu>) escribió:

>In Golang you always MUST use the Monday, January 2, 2006
>15:04:05 -7:00 reference date that you can supposedly learn and keep
>in memory by using the 0-1-2-3-4-5-6-7 trick. 0 = Monday, 1 = January,
>2 = Day 2, 3 = Hour 15, 4 = Minute 4, 5 = Second 5, 6 = Year 2006, 7 =
>Timezone -7:00 (MST). Anyone has any opinions on the Go Lang Reference
>Date Style? Pro or contra?

I always found Golang's way to specify date formatting highly confusing.
All other languages I work with use placeholders, and placeholders are
what one is used to with printf() and similar functions. Golang breaks
consistency here in my opinion. When I first read Golang's docs about
the topic, I had a hard time to understand what they want from me. Not
using placeholders came over as completely arcane and entirely unusual.

Since I have no real intention to memoise Golang's release year (2006,
appearently), I always need to pull up the reference documentation to
get the correct date. The most important strftime placeholders are easy
to learn, because they map to the first letter of the English name for
the component, but even in case I forget them, I can fire up the
strftime(3) manpage much faster than I can browse to golang.org's
reference docs.

To me, it appears as if Golang solved a problem here that never existed.

--
Blog: https://mg.guelker.eu

Unsubscribe: <mailto:ruby-talk-request@ruby-lang.org?subject=unsubscribe>
<http://lists.ruby-lang.org/cgi-bin/mailman/options/ruby-talk>

I got used to Go's formatting after a while because it's very easy to
learn (just count 0123...), but I still look up strftime(3) when I want
to format in a non-standard way.

At any rate, there are Go modules that bring strftime formatting to the
language, like there are Ruby gems that bring some other formatting to
the Ruby language. It's a matter of preference. :slight_smile:

···

On the February 17, at 16:54 (+0100), Gerald Bauer wrote:

(...)
and it works too in Ruby's date formatter (but NOT using Golang's time
format). In Golang you always MUST use the Monday, January 2, 2006
15:04:05 -7:00 reference date that you can supposedly learn and keep
in memory by using the 0-1-2-3-4-5-6-7 trick. 0 = Monday, 1 = January,
2 = Day 2, 3 = Hour 15, 4 = Minute 4, 5 = Second 5, 6 = Year 2006, 7 =
Timezone -7:00 (MST). Anyone has any opinions on the Go Lang Reference
Date Style? Pro or contra?

--
Arnaud Berthomier - https://cypr.io