mirror of
https://github.com/rails/rails.git
synced 2022-11-09 12:12:34 -05:00
Added partial days support to DateTime
's advance
method.
You can now add partial days (e.g. 2.5.days) to `DateTime` with the advance method. This was acheived by mimicing the `advance` implementation in `Time`.
This commit is contained in:
parent
f90aa722fa
commit
b2ae07f0b2
3 changed files with 25 additions and 5 deletions
|
@ -189,4 +189,8 @@
|
|||
|
||||
*Daniel Schierbeck*
|
||||
|
||||
* DateTime `advance` now supports partial days (`days: 1.5`)
|
||||
|
||||
*Shay Davidson*
|
||||
|
||||
Please check [4-0-stable](https://github.com/rails/rails/blob/4-0-stable/activesupport/CHANGELOG.md) for previous changes.
|
||||
|
|
|
@ -53,17 +53,27 @@ class DateTime
|
|||
# <tt>:months</tt>, <tt>:weeks</tt>, <tt>:days</tt>, <tt>:hours</tt>,
|
||||
# <tt>:minutes</tt>, <tt>:seconds</tt>.
|
||||
def advance(options)
|
||||
unless options[:weeks].nil?
|
||||
options[:weeks], partial_weeks = options[:weeks].divmod(1)
|
||||
options[:days] = options.fetch(:days, 0) + 7 * partial_weeks
|
||||
end
|
||||
|
||||
unless options[:days].nil?
|
||||
options[:days], partial_days = options[:days].divmod(1)
|
||||
options[:hours] = options.fetch(:hours, 0) + 24 * partial_days
|
||||
end
|
||||
|
||||
d = to_date.advance(options)
|
||||
datetime_advanced_by_date = change(:year => d.year, :month => d.month, :day => d.day)
|
||||
time_advanced_by_date = change(:year => d.year, :month => d.month, :day => d.day)
|
||||
seconds_to_advance = \
|
||||
options.fetch(:seconds, 0) +
|
||||
options.fetch(:minutes, 0) * 60 +
|
||||
options.fetch(:hours, 0) * 3600
|
||||
options.fetch(:minutes, 0) * 60 +
|
||||
options.fetch(:hours, 0) * 3600
|
||||
|
||||
if seconds_to_advance.zero?
|
||||
datetime_advanced_by_date
|
||||
time_advanced_by_date
|
||||
else
|
||||
datetime_advanced_by_date.since seconds_to_advance
|
||||
time_advanced_by_date.since(seconds_to_advance)
|
||||
end
|
||||
end
|
||||
|
||||
|
|
|
@ -162,6 +162,12 @@ class DateTimeExtCalculationsTest < ActiveSupport::TestCase
|
|||
assert_equal DateTime.civil(2013,10,17,20,22,19), DateTime.civil(2005,2,28,15,15,10).advance(:years => 7, :months => 19, :weeks => 2, :days => 5, :hours => 5, :minutes => 7, :seconds => 9)
|
||||
end
|
||||
|
||||
def test_advance_partial_days
|
||||
assert_equal DateTime.civil(2012,9,29,13,15,10), DateTime.civil(2012,9,28,1,15,10).advance(:days => 1.5)
|
||||
assert_equal DateTime.civil(2012,9,28,13,15,10), DateTime.civil(2012,9,28,1,15,10).advance(:days => 0.5)
|
||||
assert_equal DateTime.civil(2012,10,29,13,15,10), DateTime.civil(2012,9,28,1,15,10).advance(:days => 1.5, :months => 1)
|
||||
end
|
||||
|
||||
def test_advanced_processes_first_the_date_deltas_and_then_the_time_deltas
|
||||
# If the time deltas were processed first, the following datetimes would be advanced to 2010/04/01 instead.
|
||||
assert_equal DateTime.civil(2010, 3, 29), DateTime.civil(2010, 2, 28, 23, 59, 59).advance(:months => 1, :seconds => 1)
|
||||
|
|
Loading…
Reference in a new issue