Merge pull request #6077 from dmitriy-kiriyenko/improve_signature_of_time_in_words_helper

Replace boolean argument with an options hash.
This commit is contained in:
José Valim 2012-04-30 00:38:57 -07:00
commit 81f6d7f2ad
5 changed files with 96 additions and 63 deletions

View File

@ -1,5 +1,8 @@
## Rails 4.0.0 (unreleased) ## ## Rails 4.0.0 (unreleased) ##
* Replace `include_seconds` boolean argument with `:include_seconds => true` option
in `distance_of_time_in_words` and `time_ago_in_words` signature. *Dmitriy Kiriyenko*
* Remove `button_to_function` and `link_to_function` helpers. *Rafael Mendonça França* * Remove `button_to_function` and `link_to_function` helpers. *Rafael Mendonça França*
* Make current object and counter (when it applies) variables accessible when * Make current object and counter (when it applies) variables accessible when

View File

@ -19,7 +19,7 @@ module ActionView
# of \date[month]. # of \date[month].
module DateHelper module DateHelper
# Reports the approximate distance in time between two Time, Date or DateTime objects or integers as seconds. # Reports the approximate distance in time between two Time, Date or DateTime objects or integers as seconds.
# Set <tt>include_seconds</tt> to true if you want more detailed approximations when distance < 1 min, 29 secs. # Pass <tt>:include_seconds => true</tt> if you want more detailed approximations when distance < 1 min, 29 secs.
# Distances are reported based on the following table: # Distances are reported based on the following table:
# #
# 0 <-> 29 secs # => less than a minute # 0 <-> 29 secs # => less than a minute
@ -36,7 +36,7 @@ module ActionView
# 1 yr, 9 months <-> 2 yr minus 1 sec # => almost 2 years # 1 yr, 9 months <-> 2 yr minus 1 sec # => almost 2 years
# 2 yrs <-> max time or date # => (same rules as 1 yr) # 2 yrs <-> max time or date # => (same rules as 1 yr)
# #
# With <tt>include_seconds</tt> = true and the difference < 1 minute 29 seconds: # With <tt>:include_seconds => true</tt> and the difference < 1 minute 29 seconds:
# 0-4 secs # => less than 5 seconds # 0-4 secs # => less than 5 seconds
# 5-9 secs # => less than 10 seconds # 5-9 secs # => less than 10 seconds
# 10-19 secs # => less than 20 seconds # 10-19 secs # => less than 20 seconds
@ -46,28 +46,33 @@ module ActionView
# #
# ==== Examples # ==== Examples
# from_time = Time.now # from_time = Time.now
# distance_of_time_in_words(from_time, from_time + 50.minutes) # => about 1 hour # distance_of_time_in_words(from_time, from_time + 50.minutes) # => about 1 hour
# distance_of_time_in_words(from_time, 50.minutes.from_now) # => about 1 hour # distance_of_time_in_words(from_time, 50.minutes.from_now) # => about 1 hour
# distance_of_time_in_words(from_time, from_time + 15.seconds) # => less than a minute # distance_of_time_in_words(from_time, from_time + 15.seconds) # => less than a minute
# distance_of_time_in_words(from_time, from_time + 15.seconds, true) # => less than 20 seconds # distance_of_time_in_words(from_time, from_time + 15.seconds, :include_seconds => true) # => less than 20 seconds
# distance_of_time_in_words(from_time, 3.years.from_now) # => about 3 years # distance_of_time_in_words(from_time, 3.years.from_now) # => about 3 years
# distance_of_time_in_words(from_time, from_time + 60.hours) # => 3 days # distance_of_time_in_words(from_time, from_time + 60.hours) # => 3 days
# distance_of_time_in_words(from_time, from_time + 45.seconds, true) # => less than a minute # distance_of_time_in_words(from_time, from_time + 45.seconds, :include_seconds => true) # => less than a minute
# distance_of_time_in_words(from_time, from_time - 45.seconds, true) # => less than a minute # distance_of_time_in_words(from_time, from_time - 45.seconds, :include_seconds => true) # => less than a minute
# distance_of_time_in_words(from_time, 76.seconds.from_now) # => 1 minute # distance_of_time_in_words(from_time, 76.seconds.from_now) # => 1 minute
# distance_of_time_in_words(from_time, from_time + 1.year + 3.days) # => about 1 year # distance_of_time_in_words(from_time, from_time + 1.year + 3.days) # => about 1 year
# distance_of_time_in_words(from_time, from_time + 3.years + 6.months) # => over 3 years # distance_of_time_in_words(from_time, from_time + 3.years + 6.months) # => over 3 years
# distance_of_time_in_words(from_time, from_time + 4.years + 9.days + 30.minutes + 5.seconds) # => about 4 years # distance_of_time_in_words(from_time, from_time + 4.years + 9.days + 30.minutes + 5.seconds) # => about 4 years
# #
# to_time = Time.now + 6.years + 19.days # to_time = Time.now + 6.years + 19.days
# distance_of_time_in_words(from_time, to_time, true) # => about 6 years # distance_of_time_in_words(from_time, to_time, :include_seconds => true) # => about 6 years
# distance_of_time_in_words(to_time, from_time, true) # => about 6 years # distance_of_time_in_words(to_time, from_time, :include_seconds => true) # => about 6 years
# distance_of_time_in_words(Time.now, Time.now) # => less than a minute # distance_of_time_in_words(Time.now, Time.now) # => less than a minute
# #
# distance_of_time_in_words(70) # => 1 minute def distance_of_time_in_words(from_time, to_time = 0, include_seconds_or_options = {}, options = {})
# distance_of_time_in_words(60*60) # => about 1 hour unless include_seconds_or_options.is_a?(Hash)
# ActiveSupport::Deprecation.warn "distance_of_time_in_words and time_ago_in_words now accept :include_seconds " +
def distance_of_time_in_words(from_time, to_time = 0, include_seconds = false, options = {}) "as a part of options hash, not a boolean argument", caller
options[:include_seconds] ||= !!include_seconds_or_options
else
options = include_seconds_or_options
end
from_time = from_time.to_time if from_time.respond_to?(:to_time) from_time = from_time.to_time if from_time.respond_to?(:to_time)
to_time = to_time.to_time if to_time.respond_to?(:to_time) to_time = to_time.to_time if to_time.respond_to?(:to_time)
from_time, to_time = to_time, from_time if from_time > to_time from_time, to_time = to_time, from_time if from_time > to_time
@ -79,7 +84,7 @@ module ActionView
when 0..1 when 0..1
return distance_in_minutes == 0 ? return distance_in_minutes == 0 ?
locale.t(:less_than_x_minutes, :count => 1) : locale.t(:less_than_x_minutes, :count => 1) :
locale.t(:x_minutes, :count => distance_in_minutes) unless include_seconds locale.t(:x_minutes, :count => distance_in_minutes) unless options[:include_seconds]
case distance_in_seconds case distance_in_seconds
when 0..4 then locale.t :less_than_x_seconds, :count => 5 when 0..4 then locale.t :less_than_x_seconds, :count => 5
@ -130,15 +135,16 @@ module ActionView
# Like <tt>distance_of_time_in_words</tt>, but where <tt>to_time</tt> is fixed to <tt>Time.now</tt>. # Like <tt>distance_of_time_in_words</tt>, but where <tt>to_time</tt> is fixed to <tt>Time.now</tt>.
# #
# ==== Examples # ==== Examples
# time_ago_in_words(3.minutes.from_now) # => 3 minutes # time_ago_in_words(3.minutes.from_now) # => 3 minutes
# time_ago_in_words(Time.now - 15.hours) # => about 15 hours # time_ago_in_words(Time.now - 15.hours) # => about 15 hours
# time_ago_in_words(Time.now) # => less than a minute # time_ago_in_words(Time.now) # => less than a minute
# time_ago_in_words(Time.now, :include_seconds => true) # => less than 5 seconds
# #
# from_time = Time.now - 3.days - 14.minutes - 25.seconds # from_time = Time.now - 3.days - 14.minutes - 25.seconds
# time_ago_in_words(from_time) # => 3 days # time_ago_in_words(from_time) # => 3 days
# #
def time_ago_in_words(from_time, include_seconds = false) def time_ago_in_words(from_time, include_seconds_or_options = {})
distance_of_time_in_words(from_time, Time.now, include_seconds) distance_of_time_in_words(from_time, Time.now, include_seconds_or_options)
end end
alias_method :distance_of_time_in_words_to_now, :time_ago_in_words alias_method :distance_of_time_in_words_to_now, :time_ago_in_words

View File

@ -12,24 +12,24 @@ class DateHelperDistanceOfTimeInWordsI18nTests < ActiveSupport::TestCase
def test_distance_of_time_in_words_calls_i18n def test_distance_of_time_in_words_calls_i18n
{ # with include_seconds { # with include_seconds
[2.seconds, true] => [:'less_than_x_seconds', 5], [2.seconds, { :include_seconds => true }] => [:'less_than_x_seconds', 5],
[9.seconds, true] => [:'less_than_x_seconds', 10], [9.seconds, { :include_seconds => true }] => [:'less_than_x_seconds', 10],
[19.seconds, true] => [:'less_than_x_seconds', 20], [19.seconds, { :include_seconds => true }] => [:'less_than_x_seconds', 20],
[30.seconds, true] => [:'half_a_minute', nil], [30.seconds, { :include_seconds => true }] => [:'half_a_minute', nil],
[59.seconds, true] => [:'less_than_x_minutes', 1], [59.seconds, { :include_seconds => true }] => [:'less_than_x_minutes', 1],
[60.seconds, true] => [:'x_minutes', 1], [60.seconds, { :include_seconds => true }] => [:'x_minutes', 1],
# without include_seconds # without include_seconds
[29.seconds, false] => [:'less_than_x_minutes', 1], [29.seconds, { :include_seconds => false }] => [:'less_than_x_minutes', 1],
[60.seconds, false] => [:'x_minutes', 1], [60.seconds, { :include_seconds => false }] => [:'x_minutes', 1],
[44.minutes, false] => [:'x_minutes', 44], [44.minutes, { :include_seconds => false }] => [:'x_minutes', 44],
[61.minutes, false] => [:'about_x_hours', 1], [61.minutes, { :include_seconds => false }] => [:'about_x_hours', 1],
[24.hours, false] => [:'x_days', 1], [24.hours, { :include_seconds => false }] => [:'x_days', 1],
[30.days, false] => [:'about_x_months', 1], [30.days, { :include_seconds => false }] => [:'about_x_months', 1],
[60.days, false] => [:'x_months', 2], [60.days, { :include_seconds => false }] => [:'x_months', 2],
[1.year, false] => [:'about_x_years', 1], [1.year, { :include_seconds => false }] => [:'about_x_years', 1],
[3.years + 6.months, false] => [:'over_x_years', 3], [3.years + 6.months, { :include_seconds => false }] => [:'over_x_years', 3],
[3.years + 10.months, false] => [:'almost_x_years', 4] [3.years + 10.months, { :include_seconds => false }] => [:'almost_x_years', 4]
}.each do |passed, expected| }.each do |passed, expected|
assert_distance_of_time_in_words_translates_key passed, expected assert_distance_of_time_in_words_translates_key passed, expected
@ -37,7 +37,7 @@ class DateHelperDistanceOfTimeInWordsI18nTests < ActiveSupport::TestCase
end end
def assert_distance_of_time_in_words_translates_key(passed, expected) def assert_distance_of_time_in_words_translates_key(passed, expected)
diff, include_seconds = *passed diff, passed_options = *passed
key, count = *expected key, count = *expected
to = @from + diff to = @from + diff
@ -45,7 +45,12 @@ class DateHelperDistanceOfTimeInWordsI18nTests < ActiveSupport::TestCase
options[:count] = count if count options[:count] = count if count
I18n.expects(:t).with(key, options) I18n.expects(:t).with(key, options)
distance_of_time_in_words(@from, to, include_seconds, :locale => 'en') distance_of_time_in_words(@from, to, passed_options.merge(:locale => 'en'))
end
def test_time_ago_in_words_passes_locale
I18n.expects(:t).with(:less_than_x_minutes, :scope => :'datetime.distance_in_words', :count => 1, :locale => 'ru')
time_ago_in_words(15.seconds.ago, :locale => 'ru')
end end
def test_distance_of_time_pluralizations def test_distance_of_time_pluralizations

View File

@ -21,20 +21,33 @@ class DateHelperTest < ActionView::TestCase
def assert_distance_of_time_in_words(from, to=nil) def assert_distance_of_time_in_words(from, to=nil)
to ||= from to ||= from
# 0..1 with include_seconds # 0..1 with :include_seconds => true
assert_equal "less than 5 seconds", distance_of_time_in_words(from, to + 0.seconds, true) assert_equal "less than 5 seconds", distance_of_time_in_words(from, to + 0.seconds, :include_seconds => true)
assert_equal "less than 5 seconds", distance_of_time_in_words(from, to + 4.seconds, true) assert_equal "less than 5 seconds", distance_of_time_in_words(from, to + 4.seconds, :include_seconds => true)
assert_equal "less than 10 seconds", distance_of_time_in_words(from, to + 5.seconds, true) assert_equal "less than 10 seconds", distance_of_time_in_words(from, to + 5.seconds, :include_seconds => true)
assert_equal "less than 10 seconds", distance_of_time_in_words(from, to + 9.seconds, true) assert_equal "less than 10 seconds", distance_of_time_in_words(from, to + 9.seconds, :include_seconds => true)
assert_equal "less than 20 seconds", distance_of_time_in_words(from, to + 10.seconds, true) assert_equal "less than 20 seconds", distance_of_time_in_words(from, to + 10.seconds, :include_seconds => true)
assert_equal "less than 20 seconds", distance_of_time_in_words(from, to + 19.seconds, true) assert_equal "less than 20 seconds", distance_of_time_in_words(from, to + 19.seconds, :include_seconds => true)
assert_equal "half a minute", distance_of_time_in_words(from, to + 20.seconds, true) assert_equal "half a minute", distance_of_time_in_words(from, to + 20.seconds, :include_seconds => true)
assert_equal "half a minute", distance_of_time_in_words(from, to + 39.seconds, true) assert_equal "half a minute", distance_of_time_in_words(from, to + 39.seconds, :include_seconds => true)
assert_equal "less than a minute", distance_of_time_in_words(from, to + 40.seconds, true) assert_equal "less than a minute", distance_of_time_in_words(from, to + 40.seconds, :include_seconds => true)
assert_equal "less than a minute", distance_of_time_in_words(from, to + 59.seconds, true) assert_equal "less than a minute", distance_of_time_in_words(from, to + 59.seconds, :include_seconds => true)
assert_equal "1 minute", distance_of_time_in_words(from, to + 60.seconds, true) assert_equal "1 minute", distance_of_time_in_words(from, to + 60.seconds, :include_seconds => true)
assert_equal "1 minute", distance_of_time_in_words(from, to + 89.seconds, true) assert_equal "1 minute", distance_of_time_in_words(from, to + 89.seconds, :include_seconds => true)
# 0..1 with :include_seconds => false
assert_equal "less than a minute", distance_of_time_in_words(from, to + 0.seconds, :include_seconds => false)
assert_equal "less than a minute", distance_of_time_in_words(from, to + 4.seconds, :include_seconds => false)
assert_equal "less than a minute", distance_of_time_in_words(from, to + 5.seconds, :include_seconds => false)
assert_equal "less than a minute", distance_of_time_in_words(from, to + 9.seconds, :include_seconds => false)
assert_equal "less than a minute", distance_of_time_in_words(from, to + 10.seconds, :include_seconds => false)
assert_equal "less than a minute", distance_of_time_in_words(from, to + 19.seconds, :include_seconds => false)
assert_equal "less than a minute", distance_of_time_in_words(from, to + 20.seconds, :include_seconds => false)
assert_equal "1 minute", distance_of_time_in_words(from, to + 39.seconds, :include_seconds => false)
assert_equal "1 minute", distance_of_time_in_words(from, to + 40.seconds, :include_seconds => false)
assert_equal "1 minute", distance_of_time_in_words(from, to + 59.seconds, :include_seconds => false)
assert_equal "1 minute", distance_of_time_in_words(from, to + 60.seconds, :include_seconds => false)
assert_equal "1 minute", distance_of_time_in_words(from, to + 89.seconds, :include_seconds => false)
# First case 0..1 # First case 0..1
assert_equal "less than a minute", distance_of_time_in_words(from, to + 0.seconds) assert_equal "less than a minute", distance_of_time_in_words(from, to + 0.seconds)
assert_equal "less than a minute", distance_of_time_in_words(from, to + 29.seconds) assert_equal "less than a minute", distance_of_time_in_words(from, to + 29.seconds)
@ -95,7 +108,8 @@ class DateHelperTest < ActionView::TestCase
# test to < from # test to < from
assert_equal "about 4 hours", distance_of_time_in_words(from + 4.hours, to) assert_equal "about 4 hours", distance_of_time_in_words(from + 4.hours, to)
assert_equal "less than 20 seconds", distance_of_time_in_words(from + 19.seconds, to, true) assert_equal "less than 20 seconds", distance_of_time_in_words(from + 19.seconds, to, :include_seconds => true)
assert_equal "less than a minute", distance_of_time_in_words(from + 19.seconds, to, :include_seconds => false)
end end
def test_distance_in_words def test_distance_in_words
@ -103,6 +117,11 @@ class DateHelperTest < ActionView::TestCase
assert_distance_of_time_in_words(from) assert_distance_of_time_in_words(from)
end end
def test_time_ago_in_words_passes_include_seconds
assert_equal "less than 20 seconds", time_ago_in_words(15.seconds.ago, :include_seconds => true)
assert_equal "less than a minute", time_ago_in_words(15.seconds.ago, :include_seconds => false)
end
def test_distance_in_words_with_time_zones def test_distance_in_words_with_time_zones
from = Time.mktime(2004, 6, 6, 21, 45, 0) from = Time.mktime(2004, 6, 6, 21, 45, 0)
assert_distance_of_time_in_words(from.in_time_zone('Alaska')) assert_distance_of_time_in_words(from.in_time_zone('Alaska'))
@ -148,10 +167,10 @@ class DateHelperTest < ActionView::TestCase
assert_equal "about 1 hour", distance_of_time_in_words(60.minutes) assert_equal "about 1 hour", distance_of_time_in_words(60.minutes)
# include seconds # include seconds
assert_equal "half a minute", distance_of_time_in_words(39.seconds, 0, true) assert_equal "half a minute", distance_of_time_in_words(39.seconds, 0, :include_seconds => true)
assert_equal "less than a minute", distance_of_time_in_words(40.seconds, 0, true) assert_equal "less than a minute", distance_of_time_in_words(40.seconds, 0, :include_seconds => true)
assert_equal "less than a minute", distance_of_time_in_words(59.seconds, 0, true) assert_equal "less than a minute", distance_of_time_in_words(59.seconds, 0, :include_seconds => true)
assert_equal "1 minute", distance_of_time_in_words(60.seconds, 0, true) assert_equal "1 minute", distance_of_time_in_words(60.seconds, 0, :include_seconds => true)
end end
def test_time_ago_in_words def test_time_ago_in_words

View File

@ -833,7 +833,7 @@ Reports the approximate distance in time between two Time or Date objects or int
<ruby> <ruby>
distance_of_time_in_words(Time.now, Time.now + 15.seconds) # => less than a minute distance_of_time_in_words(Time.now, Time.now + 15.seconds) # => less than a minute
distance_of_time_in_words(Time.now, Time.now + 15.seconds, true) # => less than 20 seconds distance_of_time_in_words(Time.now, Time.now + 15.seconds, :include_seconds => true) # => less than 20 seconds
</ruby> </ruby>
h5. select_date h5. select_date