activesupport 4.2.11.1 → 6.0.3.1
Sign up to get free protection for your applications and to get access to all the features.
Potentially problematic release.
This version of activesupport might be problematic. Click here for more details.
- checksums.yaml +4 -4
- data/CHANGELOG.md +399 -411
- data/MIT-LICENSE +2 -2
- data/README.rdoc +7 -7
- data/lib/active_support/actionable_error.rb +48 -0
- data/lib/active_support/all.rb +5 -3
- data/lib/active_support/array_inquirer.rb +48 -0
- data/lib/active_support/backtrace_cleaner.rb +34 -6
- data/lib/active_support/benchmarkable.rb +6 -4
- data/lib/active_support/builder.rb +3 -1
- data/lib/active_support/cache/file_store.rb +58 -53
- data/lib/active_support/cache/mem_cache_store.rb +95 -91
- data/lib/active_support/cache/memory_store.rb +39 -36
- data/lib/active_support/cache/null_store.rb +11 -7
- data/lib/active_support/cache/redis_cache_store.rb +493 -0
- data/lib/active_support/cache/strategy/local_cache.rb +75 -42
- data/lib/active_support/cache/strategy/local_cache_middleware.rb +10 -9
- data/lib/active_support/cache.rb +331 -217
- data/lib/active_support/callbacks.rb +650 -592
- data/lib/active_support/concern.rb +35 -6
- data/lib/active_support/concurrency/load_interlock_aware_monitor.rb +35 -0
- data/lib/active_support/concurrency/share_lock.rb +226 -0
- data/lib/active_support/configurable.rb +13 -14
- data/lib/active_support/core_ext/array/access.rb +41 -1
- data/lib/active_support/core_ext/array/conversions.rb +24 -20
- data/lib/active_support/core_ext/array/extract.rb +21 -0
- data/lib/active_support/core_ext/array/extract_options.rb +2 -0
- data/lib/active_support/core_ext/array/grouping.rb +11 -18
- data/lib/active_support/core_ext/array/inquiry.rb +19 -0
- data/lib/active_support/core_ext/array/prepend_and_append.rb +4 -6
- data/lib/active_support/core_ext/array/wrap.rb +7 -4
- data/lib/active_support/core_ext/array.rb +9 -6
- data/lib/active_support/core_ext/benchmark.rb +3 -1
- data/lib/active_support/core_ext/big_decimal/conversions.rb +10 -12
- data/lib/active_support/core_ext/big_decimal.rb +3 -1
- data/lib/active_support/core_ext/class/attribute.rb +45 -31
- data/lib/active_support/core_ext/class/attribute_accessors.rb +3 -1
- data/lib/active_support/core_ext/class/subclasses.rb +20 -6
- data/lib/active_support/core_ext/class.rb +4 -3
- data/lib/active_support/core_ext/date/acts_like.rb +3 -1
- data/lib/active_support/core_ext/date/blank.rb +14 -0
- data/lib/active_support/core_ext/date/calculations.rb +17 -14
- data/lib/active_support/core_ext/date/conversions.rb +25 -23
- data/lib/active_support/core_ext/date/zones.rb +4 -2
- data/lib/active_support/core_ext/date.rb +6 -4
- data/lib/active_support/core_ext/date_and_time/calculations.rb +154 -65
- data/lib/active_support/core_ext/date_and_time/compatibility.rb +4 -3
- data/lib/active_support/core_ext/date_and_time/zones.rb +12 -13
- data/lib/active_support/core_ext/date_time/acts_like.rb +4 -2
- data/lib/active_support/core_ext/date_time/blank.rb +14 -0
- data/lib/active_support/core_ext/date_time/calculations.rb +37 -19
- data/lib/active_support/core_ext/date_time/compatibility.rb +8 -6
- data/lib/active_support/core_ext/date_time/conversions.rb +16 -13
- data/lib/active_support/core_ext/date_time.rb +7 -5
- data/lib/active_support/core_ext/digest/uuid.rb +7 -5
- data/lib/active_support/core_ext/digest.rb +3 -0
- data/lib/active_support/core_ext/enumerable.rb +114 -22
- data/lib/active_support/core_ext/file/atomic.rb +38 -31
- data/lib/active_support/core_ext/file.rb +3 -1
- data/lib/active_support/core_ext/hash/compact.rb +4 -23
- data/lib/active_support/core_ext/hash/conversions.rb +62 -41
- data/lib/active_support/core_ext/hash/deep_merge.rb +9 -13
- data/lib/active_support/core_ext/hash/deep_transform_values.rb +46 -0
- data/lib/active_support/core_ext/hash/except.rb +12 -9
- data/lib/active_support/core_ext/hash/indifferent_access.rb +4 -3
- data/lib/active_support/core_ext/hash/keys.rb +19 -42
- data/lib/active_support/core_ext/hash/reverse_merge.rb +5 -2
- data/lib/active_support/core_ext/hash/slice.rb +5 -27
- data/lib/active_support/core_ext/hash/transform_values.rb +4 -22
- data/lib/active_support/core_ext/hash.rb +10 -9
- data/lib/active_support/core_ext/integer/inflections.rb +3 -1
- data/lib/active_support/core_ext/integer/multiple.rb +3 -1
- data/lib/active_support/core_ext/integer/time.rb +11 -18
- data/lib/active_support/core_ext/integer.rb +5 -3
- data/lib/active_support/core_ext/kernel/concern.rb +5 -1
- data/lib/active_support/core_ext/kernel/reporting.rb +4 -84
- data/lib/active_support/core_ext/kernel/singleton_class.rb +2 -0
- data/lib/active_support/core_ext/kernel.rb +5 -5
- data/lib/active_support/core_ext/load_error.rb +3 -22
- data/lib/active_support/core_ext/marshal.rb +8 -8
- data/lib/active_support/core_ext/module/aliasing.rb +6 -44
- data/lib/active_support/core_ext/module/anonymous.rb +12 -1
- data/lib/active_support/core_ext/module/attr_internal.rb +8 -9
- data/lib/active_support/core_ext/module/attribute_accessors.rb +46 -46
- data/lib/active_support/core_ext/module/attribute_accessors_per_thread.rb +144 -0
- data/lib/active_support/core_ext/module/concerning.rb +11 -12
- data/lib/active_support/core_ext/module/delegation.rb +133 -30
- data/lib/active_support/core_ext/module/deprecation.rb +4 -2
- data/lib/active_support/core_ext/module/introspection.rb +44 -19
- data/lib/active_support/core_ext/module/reachable.rb +5 -7
- data/lib/active_support/core_ext/module/redefine_method.rb +40 -0
- data/lib/active_support/core_ext/module/remove_method.rb +8 -3
- data/lib/active_support/core_ext/module.rb +13 -11
- data/lib/active_support/core_ext/name_error.rb +22 -2
- data/lib/active_support/core_ext/numeric/bytes.rb +22 -0
- data/lib/active_support/core_ext/numeric/conversions.rb +129 -136
- data/lib/active_support/core_ext/numeric/inquiry.rb +5 -0
- data/lib/active_support/core_ext/numeric/time.rb +35 -23
- data/lib/active_support/core_ext/numeric.rb +5 -3
- data/lib/active_support/core_ext/object/acts_like.rb +12 -1
- data/lib/active_support/core_ext/object/blank.rb +27 -3
- data/lib/active_support/core_ext/object/conversions.rb +6 -4
- data/lib/active_support/core_ext/object/deep_dup.rb +13 -4
- data/lib/active_support/core_ext/object/duplicable.rb +13 -93
- data/lib/active_support/core_ext/object/inclusion.rb +5 -3
- data/lib/active_support/core_ext/object/instance_variables.rb +3 -1
- data/lib/active_support/core_ext/object/json.rb +51 -20
- data/lib/active_support/core_ext/object/to_param.rb +3 -1
- data/lib/active_support/core_ext/object/to_query.rb +10 -5
- data/lib/active_support/core_ext/object/try.rb +81 -23
- data/lib/active_support/core_ext/object/with_options.rb +16 -3
- data/lib/active_support/core_ext/object.rb +14 -13
- data/lib/active_support/core_ext/range/compare_range.rb +76 -0
- data/lib/active_support/core_ext/range/conversions.rb +37 -15
- data/lib/active_support/core_ext/range/each.rb +18 -17
- data/lib/active_support/core_ext/range/include_range.rb +7 -21
- data/lib/active_support/core_ext/range/include_time_with_zone.rb +23 -0
- data/lib/active_support/core_ext/range/overlaps.rb +2 -0
- data/lib/active_support/core_ext/range.rb +7 -4
- data/lib/active_support/core_ext/regexp.rb +2 -0
- data/lib/active_support/core_ext/securerandom.rb +45 -0
- data/lib/active_support/core_ext/string/access.rb +16 -6
- data/lib/active_support/core_ext/string/behavior.rb +3 -1
- data/lib/active_support/core_ext/string/conversions.rb +7 -4
- data/lib/active_support/core_ext/string/exclude.rb +2 -0
- data/lib/active_support/core_ext/string/filters.rb +48 -6
- data/lib/active_support/core_ext/string/indent.rb +6 -4
- data/lib/active_support/core_ext/string/inflections.rb +66 -24
- data/lib/active_support/core_ext/string/inquiry.rb +3 -1
- data/lib/active_support/core_ext/string/multibyte.rb +16 -7
- data/lib/active_support/core_ext/string/output_safety.rb +93 -40
- data/lib/active_support/core_ext/string/starts_ends_with.rb +2 -0
- data/lib/active_support/core_ext/string/strip.rb +6 -5
- data/lib/active_support/core_ext/string/zones.rb +4 -2
- data/lib/active_support/core_ext/string.rb +15 -13
- data/lib/active_support/core_ext/time/acts_like.rb +3 -1
- data/lib/active_support/core_ext/time/calculations.rb +115 -52
- data/lib/active_support/core_ext/time/compatibility.rb +4 -2
- data/lib/active_support/core_ext/time/conversions.rb +20 -13
- data/lib/active_support/core_ext/time/zones.rb +41 -7
- data/lib/active_support/core_ext/time.rb +7 -6
- data/lib/active_support/core_ext/uri.rb +6 -7
- data/lib/active_support/core_ext.rb +3 -1
- data/lib/active_support/current_attributes.rb +203 -0
- data/lib/active_support/dependencies/autoload.rb +2 -0
- data/lib/active_support/dependencies/interlock.rb +57 -0
- data/lib/active_support/dependencies/zeitwerk_integration.rb +117 -0
- data/lib/active_support/dependencies.rb +208 -166
- data/lib/active_support/deprecation/behaviors.rb +44 -11
- data/lib/active_support/deprecation/constant_accessor.rb +52 -0
- data/lib/active_support/deprecation/instance_delegator.rb +17 -2
- data/lib/active_support/deprecation/method_wrappers.rb +61 -21
- data/lib/active_support/deprecation/proxy_wrappers.rb +81 -30
- data/lib/active_support/deprecation/reporting.rb +32 -12
- data/lib/active_support/deprecation.rb +12 -9
- data/lib/active_support/descendants_tracker.rb +57 -9
- data/lib/active_support/digest.rb +20 -0
- data/lib/active_support/duration/iso8601_parser.rb +123 -0
- data/lib/active_support/duration/iso8601_serializer.rb +53 -0
- data/lib/active_support/duration.rb +315 -40
- data/lib/active_support/encrypted_configuration.rb +45 -0
- data/lib/active_support/encrypted_file.rb +100 -0
- data/lib/active_support/evented_file_update_checker.rb +234 -0
- data/lib/active_support/execution_wrapper.rb +129 -0
- data/lib/active_support/executor.rb +8 -0
- data/lib/active_support/file_update_checker.rb +62 -37
- data/lib/active_support/gem_version.rb +6 -4
- data/lib/active_support/gzip.rb +7 -5
- data/lib/active_support/hash_with_indifferent_access.rb +129 -30
- data/lib/active_support/i18n.rb +9 -6
- data/lib/active_support/i18n_railtie.rb +50 -14
- data/lib/active_support/inflections.rb +13 -11
- data/lib/active_support/inflector/inflections.rb +58 -13
- data/lib/active_support/inflector/methods.rb +159 -145
- data/lib/active_support/inflector/transliterate.rb +84 -34
- data/lib/active_support/inflector.rb +7 -5
- data/lib/active_support/json/decoding.rb +32 -30
- data/lib/active_support/json/encoding.rb +17 -60
- data/lib/active_support/json.rb +4 -2
- data/lib/active_support/key_generator.rb +11 -43
- data/lib/active_support/lazy_load_hooks.rb +53 -20
- data/lib/active_support/locale/en.rb +33 -0
- data/lib/active_support/locale/en.yml +2 -0
- data/lib/active_support/log_subscriber/test_helper.rb +14 -12
- data/lib/active_support/log_subscriber.rb +44 -19
- data/lib/active_support/logger.rb +9 -23
- data/lib/active_support/logger_silence.rb +32 -14
- data/lib/active_support/logger_thread_safe_level.rb +32 -8
- data/lib/active_support/message_encryptor.rb +166 -53
- data/lib/active_support/message_verifier.rb +149 -16
- data/lib/active_support/messages/metadata.rb +72 -0
- data/lib/active_support/messages/rotation_configuration.rb +22 -0
- data/lib/active_support/messages/rotator.rb +56 -0
- data/lib/active_support/multibyte/chars.rb +56 -63
- data/lib/active_support/multibyte/unicode.rb +56 -290
- data/lib/active_support/multibyte.rb +4 -2
- data/lib/active_support/notifications/fanout.rb +109 -22
- data/lib/active_support/notifications/instrumenter.rb +107 -16
- data/lib/active_support/notifications.rb +51 -10
- data/lib/active_support/number_helper/number_converter.rb +16 -15
- data/lib/active_support/number_helper/number_to_currency_converter.rb +14 -15
- data/lib/active_support/number_helper/number_to_delimited_converter.rb +11 -4
- data/lib/active_support/number_helper/number_to_human_converter.rb +13 -10
- data/lib/active_support/number_helper/number_to_human_size_converter.rb +11 -9
- data/lib/active_support/number_helper/number_to_percentage_converter.rb +5 -1
- data/lib/active_support/number_helper/number_to_phone_converter.rb +15 -5
- data/lib/active_support/number_helper/number_to_rounded_converter.rb +25 -57
- data/lib/active_support/number_helper/rounding_helper.rb +66 -0
- data/lib/active_support/number_helper.rb +105 -68
- data/lib/active_support/option_merger.rb +24 -4
- data/lib/active_support/ordered_hash.rb +7 -5
- data/lib/active_support/ordered_options.rb +27 -5
- data/lib/active_support/parameter_filter.rb +128 -0
- data/lib/active_support/per_thread_registry.rb +9 -4
- data/lib/active_support/proxy_object.rb +2 -0
- data/lib/active_support/rails.rb +10 -8
- data/lib/active_support/railtie.rb +43 -9
- data/lib/active_support/reloader.rb +130 -0
- data/lib/active_support/rescuable.rb +108 -53
- data/lib/active_support/security_utils.rb +15 -11
- data/lib/active_support/string_inquirer.rb +11 -4
- data/lib/active_support/subscriber.rb +74 -30
- data/lib/active_support/tagged_logging.rb +25 -13
- data/lib/active_support/test_case.rb +107 -44
- data/lib/active_support/testing/assertions.rb +151 -20
- data/lib/active_support/testing/autorun.rb +4 -2
- data/lib/active_support/testing/constant_lookup.rb +2 -1
- data/lib/active_support/testing/declarative.rb +3 -1
- data/lib/active_support/testing/deprecation.rb +13 -10
- data/lib/active_support/testing/file_fixtures.rb +38 -0
- data/lib/active_support/testing/isolation.rb +35 -26
- data/lib/active_support/testing/method_call_assertions.rb +70 -0
- data/lib/active_support/testing/parallelization.rb +134 -0
- data/lib/active_support/testing/setup_and_teardown.rb +13 -8
- data/lib/active_support/testing/stream.rb +43 -0
- data/lib/active_support/testing/tagged_logging.rb +3 -1
- data/lib/active_support/testing/time_helpers.rb +84 -20
- data/lib/active_support/time.rb +14 -12
- data/lib/active_support/time_with_zone.rb +179 -39
- data/lib/active_support/values/time_zone.rb +203 -63
- data/lib/active_support/version.rb +3 -1
- data/lib/active_support/xml_mini/jdom.rb +116 -115
- data/lib/active_support/xml_mini/libxml.rb +16 -13
- data/lib/active_support/xml_mini/libxmlsax.rb +15 -14
- data/lib/active_support/xml_mini/nokogiri.rb +14 -12
- data/lib/active_support/xml_mini/nokogirisax.rb +14 -13
- data/lib/active_support/xml_mini/rexml.rb +11 -9
- data/lib/active_support/xml_mini.rb +38 -46
- data/lib/active_support.rb +13 -11
- metadata +84 -26
- data/lib/active_support/concurrency/latch.rb +0 -27
- data/lib/active_support/core_ext/big_decimal/yaml_conversions.rb +0 -16
- data/lib/active_support/core_ext/class/delegating_attributes.rb +0 -45
- data/lib/active_support/core_ext/date_time/zones.rb +0 -6
- data/lib/active_support/core_ext/kernel/agnostics.rb +0 -11
- data/lib/active_support/core_ext/kernel/debugger.rb +0 -10
- data/lib/active_support/core_ext/module/method_transplanting.rb +0 -13
- data/lib/active_support/core_ext/module/qualified_const.rb +0 -52
- data/lib/active_support/core_ext/object/itself.rb +0 -15
- data/lib/active_support/core_ext/struct.rb +0 -6
- data/lib/active_support/core_ext/thread.rb +0 -86
- data/lib/active_support/core_ext/time/marshal.rb +0 -30
- data/lib/active_support/values/unicode_tables.dat +0 -0
@@ -1,48 +1,63 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "active_support/core_ext/module/redefine_method"
|
4
|
+
require "active_support/core_ext/time/calculations"
|
5
|
+
require "concurrent/map"
|
6
|
+
|
1
7
|
module ActiveSupport
|
2
8
|
module Testing
|
3
9
|
class SimpleStubs # :nodoc:
|
4
10
|
Stub = Struct.new(:object, :method_name, :original_method)
|
5
11
|
|
6
12
|
def initialize
|
7
|
-
@stubs = {}
|
13
|
+
@stubs = Concurrent::Map.new { |h, k| h[k] = {} }
|
8
14
|
end
|
9
15
|
|
10
16
|
def stub_object(object, method_name, &block)
|
11
|
-
|
12
|
-
|
13
|
-
if stub = @stubs[key]
|
17
|
+
if stub = stubbing(object, method_name)
|
14
18
|
unstub_object(stub)
|
15
19
|
end
|
16
20
|
|
17
21
|
new_name = "__simple_stub__#{method_name}"
|
18
22
|
|
19
|
-
@stubs[
|
23
|
+
@stubs[object.object_id][method_name] = Stub.new(object, method_name, new_name)
|
20
24
|
|
21
|
-
object.singleton_class.
|
25
|
+
object.singleton_class.alias_method new_name, method_name
|
22
26
|
object.define_singleton_method(method_name, &block)
|
23
27
|
end
|
24
28
|
|
25
29
|
def unstub_all!
|
26
|
-
@stubs.each_value do |
|
27
|
-
|
30
|
+
@stubs.each_value do |object_stubs|
|
31
|
+
object_stubs.each_value do |stub|
|
32
|
+
unstub_object(stub)
|
33
|
+
end
|
28
34
|
end
|
29
|
-
@stubs
|
35
|
+
@stubs.clear
|
30
36
|
end
|
31
37
|
|
32
|
-
|
38
|
+
def stubbing(object, method_name)
|
39
|
+
@stubs[object.object_id][method_name]
|
40
|
+
end
|
33
41
|
|
42
|
+
private
|
34
43
|
def unstub_object(stub)
|
35
44
|
singleton_class = stub.object.singleton_class
|
36
|
-
singleton_class.
|
37
|
-
singleton_class.
|
38
|
-
singleton_class.
|
45
|
+
singleton_class.silence_redefinition_of_method stub.method_name
|
46
|
+
singleton_class.alias_method stub.method_name, stub.original_method
|
47
|
+
singleton_class.undef_method stub.original_method
|
39
48
|
end
|
40
49
|
end
|
41
50
|
|
42
|
-
#
|
51
|
+
# Contains helpers that help you test passage of time.
|
43
52
|
module TimeHelpers
|
53
|
+
def after_teardown
|
54
|
+
travel_back
|
55
|
+
super
|
56
|
+
end
|
57
|
+
|
44
58
|
# Changes current time to the time in the future or in the past by a given time difference by
|
45
|
-
# stubbing +Time.now+, +Date.today+, and +DateTime.now+.
|
59
|
+
# stubbing +Time.now+, +Date.today+, and +DateTime.now+. The stubs are automatically removed
|
60
|
+
# at the end of the test.
|
46
61
|
#
|
47
62
|
# Time.current # => Sat, 09 Nov 2013 15:34:49 EST -05:00
|
48
63
|
# travel 1.day
|
@@ -64,9 +79,10 @@ module ActiveSupport
|
|
64
79
|
|
65
80
|
# Changes current time to the given time by stubbing +Time.now+,
|
66
81
|
# +Date.today+, and +DateTime.now+ to return the time or date passed into this method.
|
82
|
+
# The stubs are automatically removed at the end of the test.
|
67
83
|
#
|
68
84
|
# Time.current # => Sat, 09 Nov 2013 15:34:49 EST -05:00
|
69
|
-
# travel_to Time.
|
85
|
+
# travel_to Time.zone.local(2004, 11, 24, 01, 04, 44)
|
70
86
|
# Time.current # => Wed, 24 Nov 2004 01:04:44 EST -05:00
|
71
87
|
# Date.current # => Wed, 24 Nov 2004
|
72
88
|
# DateTime.current # => Wed, 24 Nov 2004 01:04:44 -0500
|
@@ -88,11 +104,39 @@ module ActiveSupport
|
|
88
104
|
# state at the end of the block:
|
89
105
|
#
|
90
106
|
# Time.current # => Sat, 09 Nov 2013 15:34:49 EST -05:00
|
91
|
-
# travel_to Time.
|
107
|
+
# travel_to Time.zone.local(2004, 11, 24, 01, 04, 44) do
|
92
108
|
# Time.current # => Wed, 24 Nov 2004 01:04:44 EST -05:00
|
93
109
|
# end
|
94
110
|
# Time.current # => Sat, 09 Nov 2013 15:34:49 EST -05:00
|
95
111
|
def travel_to(date_or_time)
|
112
|
+
if block_given? && simple_stubs.stubbing(Time, :now)
|
113
|
+
travel_to_nested_block_call = <<~MSG
|
114
|
+
|
115
|
+
Calling `travel_to` with a block, when we have previously already made a call to `travel_to`, can lead to confusing time stubbing.
|
116
|
+
|
117
|
+
Instead of:
|
118
|
+
|
119
|
+
travel_to 2.days.from_now do
|
120
|
+
# 2 days from today
|
121
|
+
travel_to 3.days.from_now do
|
122
|
+
# 5 days from today
|
123
|
+
end
|
124
|
+
end
|
125
|
+
|
126
|
+
preferred way to achieve above is:
|
127
|
+
|
128
|
+
travel 2.days do
|
129
|
+
# 2 days from today
|
130
|
+
end
|
131
|
+
|
132
|
+
travel 5.days do
|
133
|
+
# 5 days from today
|
134
|
+
end
|
135
|
+
|
136
|
+
MSG
|
137
|
+
raise travel_to_nested_block_call
|
138
|
+
end
|
139
|
+
|
96
140
|
if date_or_time.is_a?(Date) && !date_or_time.is_a?(DateTime)
|
97
141
|
now = date_or_time.midnight.to_time
|
98
142
|
else
|
@@ -113,19 +157,39 @@ module ActiveSupport
|
|
113
157
|
end
|
114
158
|
|
115
159
|
# Returns the current time back to its original state, by removing the stubs added by
|
116
|
-
#
|
160
|
+
# +travel+, +travel_to+, and +freeze_time+.
|
117
161
|
#
|
118
162
|
# Time.current # => Sat, 09 Nov 2013 15:34:49 EST -05:00
|
119
|
-
# travel_to Time.
|
163
|
+
# travel_to Time.zone.local(2004, 11, 24, 01, 04, 44)
|
120
164
|
# Time.current # => Wed, 24 Nov 2004 01:04:44 EST -05:00
|
121
165
|
# travel_back
|
122
166
|
# Time.current # => Sat, 09 Nov 2013 15:34:49 EST -05:00
|
123
167
|
def travel_back
|
124
168
|
simple_stubs.unstub_all!
|
125
169
|
end
|
170
|
+
alias_method :unfreeze_time, :travel_back
|
126
171
|
|
127
|
-
|
172
|
+
# Calls +travel_to+ with +Time.now+.
|
173
|
+
#
|
174
|
+
# Time.current # => Sun, 09 Jul 2017 15:34:49 EST -05:00
|
175
|
+
# freeze_time
|
176
|
+
# sleep(1)
|
177
|
+
# Time.current # => Sun, 09 Jul 2017 15:34:49 EST -05:00
|
178
|
+
#
|
179
|
+
# This method also accepts a block, which will return the current time back to its original
|
180
|
+
# state at the end of the block:
|
181
|
+
#
|
182
|
+
# Time.current # => Sun, 09 Jul 2017 15:34:49 EST -05:00
|
183
|
+
# freeze_time do
|
184
|
+
# sleep(1)
|
185
|
+
# User.create.created_at # => Sun, 09 Jul 2017 15:34:49 EST -05:00
|
186
|
+
# end
|
187
|
+
# Time.current # => Sun, 09 Jul 2017 15:34:50 EST -05:00
|
188
|
+
def freeze_time(&block)
|
189
|
+
travel_to Time.now, &block
|
190
|
+
end
|
128
191
|
|
192
|
+
private
|
129
193
|
def simple_stubs
|
130
194
|
@simple_stubs ||= SimpleStubs.new
|
131
195
|
end
|
data/lib/active_support/time.rb
CHANGED
@@ -1,18 +1,20 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
module ActiveSupport
|
2
|
-
autoload :Duration,
|
3
|
-
autoload :TimeWithZone,
|
4
|
-
autoload :TimeZone,
|
4
|
+
autoload :Duration, "active_support/duration"
|
5
|
+
autoload :TimeWithZone, "active_support/time_with_zone"
|
6
|
+
autoload :TimeZone, "active_support/values/time_zone"
|
5
7
|
end
|
6
8
|
|
7
|
-
require
|
8
|
-
require
|
9
|
+
require "date"
|
10
|
+
require "time"
|
9
11
|
|
10
|
-
require
|
11
|
-
require
|
12
|
-
require
|
12
|
+
require "active_support/core_ext/time"
|
13
|
+
require "active_support/core_ext/date"
|
14
|
+
require "active_support/core_ext/date_time"
|
13
15
|
|
14
|
-
require
|
15
|
-
require
|
16
|
+
require "active_support/core_ext/integer/time"
|
17
|
+
require "active_support/core_ext/numeric/time"
|
16
18
|
|
17
|
-
require
|
18
|
-
require
|
19
|
+
require "active_support/core_ext/string/conversions"
|
20
|
+
require "active_support/core_ext/string/zones"
|
@@ -1,6 +1,9 @@
|
|
1
|
-
|
2
|
-
|
3
|
-
require
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "active_support/duration"
|
4
|
+
require "active_support/values/time_zone"
|
5
|
+
require "active_support/core_ext/object/acts_like"
|
6
|
+
require "active_support/core_ext/date_and_time/compatibility"
|
4
7
|
|
5
8
|
module ActiveSupport
|
6
9
|
# A Time-like class that can represent a time in any time zone. Necessary
|
@@ -14,7 +17,7 @@ module ActiveSupport
|
|
14
17
|
# Time.zone = 'Eastern Time (US & Canada)' # => 'Eastern Time (US & Canada)'
|
15
18
|
# Time.zone.local(2007, 2, 10, 15, 30, 45) # => Sat, 10 Feb 2007 15:30:45 EST -05:00
|
16
19
|
# Time.zone.parse('2007-02-10 15:30:45') # => Sat, 10 Feb 2007 15:30:45 EST -05:00
|
17
|
-
# Time.zone.at(
|
20
|
+
# Time.zone.at(1171139445) # => Sat, 10 Feb 2007 15:30:45 EST -05:00
|
18
21
|
# Time.zone.now # => Sun, 18 May 2008 13:07:55 EDT -04:00
|
19
22
|
# Time.utc(2007, 2, 10, 20, 30, 45).in_time_zone # => Sat, 10 Feb 2007 15:30:45 EST -05:00
|
20
23
|
#
|
@@ -35,12 +38,14 @@ module ActiveSupport
|
|
35
38
|
# t.is_a?(Time) # => true
|
36
39
|
# t.is_a?(ActiveSupport::TimeWithZone) # => true
|
37
40
|
class TimeWithZone
|
38
|
-
|
39
41
|
# Report class name as 'Time' to thwart type checking.
|
40
42
|
def self.name
|
41
|
-
|
43
|
+
"Time"
|
42
44
|
end
|
43
45
|
|
46
|
+
PRECISIONS = Hash.new { |h, n| h[n] = "%FT%T.%#{n}N" }
|
47
|
+
PRECISIONS[0] = "%FT%T"
|
48
|
+
|
44
49
|
include Comparable, DateAndTime::Compatibility
|
45
50
|
attr_reader :time_zone
|
46
51
|
|
@@ -99,7 +104,7 @@ module ActiveSupport
|
|
99
104
|
# Time.zone = 'Eastern Time (US & Canada)' # => 'Eastern Time (US & Canada)'
|
100
105
|
# Time.zone.now.utc? # => false
|
101
106
|
def utc?
|
102
|
-
|
107
|
+
period.offset.abbreviation == :UTC || period.offset.abbreviation == :UCT
|
103
108
|
end
|
104
109
|
alias_method :gmt?, :utc?
|
105
110
|
|
@@ -122,24 +127,30 @@ module ActiveSupport
|
|
122
127
|
utc? && alternate_utc_string || TimeZone.seconds_to_utc_offset(utc_offset, colon)
|
123
128
|
end
|
124
129
|
|
125
|
-
#
|
126
|
-
#
|
130
|
+
# Returns the time zone abbreviation.
|
131
|
+
#
|
132
|
+
# Time.zone = 'Eastern Time (US & Canada)' # => "Eastern Time (US & Canada)"
|
133
|
+
# Time.zone.now.zone # => "EST"
|
127
134
|
def zone
|
128
135
|
period.zone_identifier.to_s
|
129
136
|
end
|
130
137
|
|
138
|
+
# Returns a string of the object's date, time, zone, and offset from UTC.
|
139
|
+
#
|
140
|
+
# Time.zone.now.inspect # => "Thu, 04 Dec 2014 11:00:25 EST -05:00"
|
131
141
|
def inspect
|
132
142
|
"#{time.strftime('%a, %d %b %Y %H:%M:%S')} #{zone} #{formatted_offset}"
|
133
143
|
end
|
134
144
|
|
145
|
+
# Returns a string of the object's date and time in the ISO 8601 standard
|
146
|
+
# format.
|
147
|
+
#
|
148
|
+
# Time.zone.now.xmlschema # => "2014-12-04T11:02:37-05:00"
|
135
149
|
def xmlschema(fraction_digits = 0)
|
136
|
-
|
137
|
-
(".%06i" % time.usec)[0, fraction_digits.to_i + 1]
|
138
|
-
end
|
139
|
-
|
140
|
-
"#{time.strftime("%Y-%m-%dT%H:%M:%S")}#{fraction}#{formatted_offset(true, 'Z')}"
|
150
|
+
"#{time.strftime(PRECISIONS[fraction_digits.to_i])}#{formatted_offset(true, 'Z')}"
|
141
151
|
end
|
142
152
|
alias_method :iso8601, :xmlschema
|
153
|
+
alias_method :rfc3339, :xmlschema
|
143
154
|
|
144
155
|
# Coerces time to a string for JSON encoding. The default format is ISO 8601.
|
145
156
|
# You can get %Y/%m/%d %H:%M:%S +offset style by setting
|
@@ -162,15 +173,12 @@ module ActiveSupport
|
|
162
173
|
end
|
163
174
|
|
164
175
|
def init_with(coder) #:nodoc:
|
165
|
-
initialize(coder[
|
176
|
+
initialize(coder["utc"], coder["zone"], coder["time"])
|
166
177
|
end
|
167
178
|
|
168
179
|
def encode_with(coder) #:nodoc:
|
169
|
-
|
170
|
-
|
171
|
-
else
|
172
|
-
coder.represent_scalar(nil, utc.strftime("%Y-%m-%d %H:%M:%S.%9NZ"))
|
173
|
-
end
|
180
|
+
coder.tag = "!ruby/object:ActiveSupport::TimeWithZone"
|
181
|
+
coder.map = { "utc" => utc, "zone" => time_zone, "time" => time }
|
174
182
|
end
|
175
183
|
|
176
184
|
# Returns a string of the object's date and time in the format used by
|
@@ -192,7 +200,7 @@ module ActiveSupport
|
|
192
200
|
|
193
201
|
# Returns a string of the object's date and time.
|
194
202
|
# Accepts an optional <tt>format</tt>:
|
195
|
-
# * <tt>:default</tt> - default value, mimics Ruby
|
203
|
+
# * <tt>:default</tt> - default value, mimics Ruby Time#to_s format.
|
196
204
|
# * <tt>:db</tt> - format outputs time in UTC :db time. See Time#to_formatted_s(:db).
|
197
205
|
# * Any key in <tt>Time::DATE_FORMATS</tt> can be used. See active_support/core_ext/time/conversions.rb.
|
198
206
|
def to_s(format = :default)
|
@@ -201,7 +209,7 @@ module ActiveSupport
|
|
201
209
|
elsif formatter = ::Time::DATE_FORMATS[format]
|
202
210
|
formatter.respond_to?(:call) ? formatter.call(self).to_s : strftime(formatter)
|
203
211
|
else
|
204
|
-
"#{time.strftime("%Y-%m-%d %H:%M:%S")} #{formatted_offset(false, 'UTC')}" # mimicking Ruby
|
212
|
+
"#{time.strftime("%Y-%m-%d %H:%M:%S")} #{formatted_offset(false, 'UTC')}" # mimicking Ruby Time#to_s format
|
205
213
|
end
|
206
214
|
end
|
207
215
|
alias_method :to_formatted_s, :to_s
|
@@ -217,6 +225,8 @@ module ActiveSupport
|
|
217
225
|
def <=>(other)
|
218
226
|
utc <=> other
|
219
227
|
end
|
228
|
+
alias_method :before?, :<
|
229
|
+
alias_method :after?, :>
|
220
230
|
|
221
231
|
# Returns true if the current object's time is within the specified
|
222
232
|
# +min+ and +max+ time.
|
@@ -240,6 +250,7 @@ module ActiveSupport
|
|
240
250
|
utc.future?
|
241
251
|
end
|
242
252
|
|
253
|
+
# Returns +true+ if +other+ is equal to current object.
|
243
254
|
def eql?(other)
|
244
255
|
other.eql?(utc)
|
245
256
|
end
|
@@ -248,9 +259,23 @@ module ActiveSupport
|
|
248
259
|
utc.hash
|
249
260
|
end
|
250
261
|
|
262
|
+
# Adds an interval of time to the current object's time and returns that
|
263
|
+
# value as a new TimeWithZone object.
|
264
|
+
#
|
265
|
+
# Time.zone = 'Eastern Time (US & Canada)' # => 'Eastern Time (US & Canada)'
|
266
|
+
# now = Time.zone.now # => Sun, 02 Nov 2014 01:26:28 EDT -04:00
|
267
|
+
# now + 1000 # => Sun, 02 Nov 2014 01:43:08 EDT -04:00
|
268
|
+
#
|
269
|
+
# If we're adding a Duration of variable length (i.e., years, months, days),
|
270
|
+
# move forward from #time, otherwise move forward from #utc, for accuracy
|
271
|
+
# when moving across DST boundaries.
|
272
|
+
#
|
273
|
+
# For instance, a time + 24.hours will advance exactly 24 hours, while a
|
274
|
+
# time + 1.day will advance 23-25 hours, depending on the day.
|
275
|
+
#
|
276
|
+
# now + 24.hours # => Mon, 03 Nov 2014 00:26:28 EST -05:00
|
277
|
+
# now + 1.day # => Mon, 03 Nov 2014 01:26:28 EST -05:00
|
251
278
|
def +(other)
|
252
|
-
# If we're adding a Duration of variable length (i.e., years, months, days), move forward from #time,
|
253
|
-
# otherwise move forward from #utc, for accuracy when moving across DST boundaries
|
254
279
|
if duration_of_variable_length?(other)
|
255
280
|
method_missing(:+, other)
|
256
281
|
else
|
@@ -258,10 +283,34 @@ module ActiveSupport
|
|
258
283
|
result.in_time_zone(time_zone)
|
259
284
|
end
|
260
285
|
end
|
286
|
+
alias_method :since, :+
|
287
|
+
alias_method :in, :+
|
261
288
|
|
289
|
+
# Subtracts an interval of time and returns a new TimeWithZone object unless
|
290
|
+
# the other value `acts_like?` time. Then it will return a Float of the difference
|
291
|
+
# between the two times that represents the difference between the current
|
292
|
+
# object's time and the +other+ time.
|
293
|
+
#
|
294
|
+
# Time.zone = 'Eastern Time (US & Canada)' # => 'Eastern Time (US & Canada)'
|
295
|
+
# now = Time.zone.now # => Mon, 03 Nov 2014 00:26:28 EST -05:00
|
296
|
+
# now - 1000 # => Mon, 03 Nov 2014 00:09:48 EST -05:00
|
297
|
+
#
|
298
|
+
# If subtracting a Duration of variable length (i.e., years, months, days),
|
299
|
+
# move backward from #time, otherwise move backward from #utc, for accuracy
|
300
|
+
# when moving across DST boundaries.
|
301
|
+
#
|
302
|
+
# For instance, a time - 24.hours will go subtract exactly 24 hours, while a
|
303
|
+
# time - 1.day will subtract 23-25 hours, depending on the day.
|
304
|
+
#
|
305
|
+
# now - 24.hours # => Sun, 02 Nov 2014 01:26:28 EDT -04:00
|
306
|
+
# now - 1.day # => Sun, 02 Nov 2014 00:26:28 EDT -04:00
|
307
|
+
#
|
308
|
+
# If both the TimeWithZone object and the other value act like Time, a Float
|
309
|
+
# will be returned.
|
310
|
+
#
|
311
|
+
# Time.zone.now - 1.day.ago # => 86399.999967
|
312
|
+
#
|
262
313
|
def -(other)
|
263
|
-
# If we're subtracting a Duration of variable length (i.e., years, months, days), move backwards from #time,
|
264
|
-
# otherwise move backwards #utc, for accuracy when moving across DST boundaries
|
265
314
|
if other.acts_like?(:time)
|
266
315
|
to_time - other.to_time
|
267
316
|
elsif duration_of_variable_length?(other)
|
@@ -272,21 +321,84 @@ module ActiveSupport
|
|
272
321
|
end
|
273
322
|
end
|
274
323
|
|
275
|
-
|
276
|
-
|
277
|
-
|
278
|
-
|
279
|
-
|
280
|
-
|
281
|
-
|
282
|
-
|
283
|
-
|
284
|
-
|
285
|
-
|
324
|
+
# Subtracts an interval of time from the current object's time and returns
|
325
|
+
# the result as a new TimeWithZone object.
|
326
|
+
#
|
327
|
+
# Time.zone = 'Eastern Time (US & Canada)' # => 'Eastern Time (US & Canada)'
|
328
|
+
# now = Time.zone.now # => Mon, 03 Nov 2014 00:26:28 EST -05:00
|
329
|
+
# now.ago(1000) # => Mon, 03 Nov 2014 00:09:48 EST -05:00
|
330
|
+
#
|
331
|
+
# If we're subtracting a Duration of variable length (i.e., years, months,
|
332
|
+
# days), move backward from #time, otherwise move backward from #utc, for
|
333
|
+
# accuracy when moving across DST boundaries.
|
334
|
+
#
|
335
|
+
# For instance, <tt>time.ago(24.hours)</tt> will move back exactly 24 hours,
|
336
|
+
# while <tt>time.ago(1.day)</tt> will move back 23-25 hours, depending on
|
337
|
+
# the day.
|
338
|
+
#
|
339
|
+
# now.ago(24.hours) # => Sun, 02 Nov 2014 01:26:28 EDT -04:00
|
340
|
+
# now.ago(1.day) # => Sun, 02 Nov 2014 00:26:28 EDT -04:00
|
286
341
|
def ago(other)
|
287
342
|
since(-other)
|
288
343
|
end
|
289
344
|
|
345
|
+
# Returns a new +ActiveSupport::TimeWithZone+ where one or more of the elements have
|
346
|
+
# been changed according to the +options+ parameter. The time options (<tt>:hour</tt>,
|
347
|
+
# <tt>:min</tt>, <tt>:sec</tt>, <tt>:usec</tt>, <tt>:nsec</tt>) reset cascadingly,
|
348
|
+
# so if only the hour is passed, then minute, sec, usec and nsec is set to 0. If the
|
349
|
+
# hour and minute is passed, then sec, usec and nsec is set to 0. The +options+
|
350
|
+
# parameter takes a hash with any of these keys: <tt>:year</tt>, <tt>:month</tt>,
|
351
|
+
# <tt>:day</tt>, <tt>:hour</tt>, <tt>:min</tt>, <tt>:sec</tt>, <tt>:usec</tt>,
|
352
|
+
# <tt>:nsec</tt>, <tt>:offset</tt>, <tt>:zone</tt>. Pass either <tt>:usec</tt>
|
353
|
+
# or <tt>:nsec</tt>, not both. Similarly, pass either <tt>:zone</tt> or
|
354
|
+
# <tt>:offset</tt>, not both.
|
355
|
+
#
|
356
|
+
# t = Time.zone.now # => Fri, 14 Apr 2017 11:45:15 EST -05:00
|
357
|
+
# t.change(year: 2020) # => Tue, 14 Apr 2020 11:45:15 EST -05:00
|
358
|
+
# t.change(hour: 12) # => Fri, 14 Apr 2017 12:00:00 EST -05:00
|
359
|
+
# t.change(min: 30) # => Fri, 14 Apr 2017 11:30:00 EST -05:00
|
360
|
+
# t.change(offset: "-10:00") # => Fri, 14 Apr 2017 11:45:15 HST -10:00
|
361
|
+
# t.change(zone: "Hawaii") # => Fri, 14 Apr 2017 11:45:15 HST -10:00
|
362
|
+
def change(options)
|
363
|
+
if options[:zone] && options[:offset]
|
364
|
+
raise ArgumentError, "Can't change both :offset and :zone at the same time: #{options.inspect}"
|
365
|
+
end
|
366
|
+
|
367
|
+
new_time = time.change(options)
|
368
|
+
|
369
|
+
if options[:zone]
|
370
|
+
new_zone = ::Time.find_zone(options[:zone])
|
371
|
+
elsif options[:offset]
|
372
|
+
new_zone = ::Time.find_zone(new_time.utc_offset)
|
373
|
+
end
|
374
|
+
|
375
|
+
new_zone ||= time_zone
|
376
|
+
periods = new_zone.periods_for_local(new_time)
|
377
|
+
|
378
|
+
self.class.new(nil, new_zone, new_time, periods.include?(period) ? period : nil)
|
379
|
+
end
|
380
|
+
|
381
|
+
# Uses Date to provide precise Time calculations for years, months, and days
|
382
|
+
# according to the proleptic Gregorian calendar. The result is returned as a
|
383
|
+
# new TimeWithZone object.
|
384
|
+
#
|
385
|
+
# The +options+ parameter takes a hash with any of these keys:
|
386
|
+
# <tt>:years</tt>, <tt>:months</tt>, <tt>:weeks</tt>, <tt>:days</tt>,
|
387
|
+
# <tt>:hours</tt>, <tt>:minutes</tt>, <tt>:seconds</tt>.
|
388
|
+
#
|
389
|
+
# If advancing by a value of variable length (i.e., years, weeks, months,
|
390
|
+
# days), move forward from #time, otherwise move forward from #utc, for
|
391
|
+
# accuracy when moving across DST boundaries.
|
392
|
+
#
|
393
|
+
# Time.zone = 'Eastern Time (US & Canada)' # => 'Eastern Time (US & Canada)'
|
394
|
+
# now = Time.zone.now # => Sun, 02 Nov 2014 01:26:28 EDT -04:00
|
395
|
+
# now.advance(seconds: 1) # => Sun, 02 Nov 2014 01:26:29 EDT -04:00
|
396
|
+
# now.advance(minutes: 1) # => Sun, 02 Nov 2014 01:27:28 EDT -04:00
|
397
|
+
# now.advance(hours: 1) # => Sun, 02 Nov 2014 01:26:28 EST -05:00
|
398
|
+
# now.advance(days: 1) # => Mon, 03 Nov 2014 01:26:28 EST -05:00
|
399
|
+
# now.advance(weeks: 1) # => Sun, 09 Nov 2014 01:26:28 EST -05:00
|
400
|
+
# now.advance(months: 1) # => Tue, 02 Dec 2014 01:26:28 EST -05:00
|
401
|
+
# now.advance(years: 1) # => Mon, 02 Nov 2015 01:26:28 EST -05:00
|
290
402
|
def advance(options)
|
291
403
|
# If we're advancing a value of variable length (i.e., years, weeks, months, days), advance from #time,
|
292
404
|
# otherwise advance from #utc, for accuracy when moving across DST boundaries
|
@@ -305,23 +417,44 @@ module ActiveSupport
|
|
305
417
|
EOV
|
306
418
|
end
|
307
419
|
|
420
|
+
# Returns Array of parts of Time in sequence of
|
421
|
+
# [seconds, minutes, hours, day, month, year, weekday, yearday, dst?, zone].
|
422
|
+
#
|
423
|
+
# now = Time.zone.now # => Tue, 18 Aug 2015 02:29:27 UTC +00:00
|
424
|
+
# now.to_a # => [27, 29, 2, 18, 8, 2015, 2, 230, false, "UTC"]
|
308
425
|
def to_a
|
309
426
|
[time.sec, time.min, time.hour, time.day, time.mon, time.year, time.wday, time.yday, dst?, zone]
|
310
427
|
end
|
311
428
|
|
429
|
+
# Returns the object's date and time as a floating point number of seconds
|
430
|
+
# since the Epoch (January 1, 1970 00:00 UTC).
|
431
|
+
#
|
432
|
+
# Time.zone.now.to_f # => 1417709320.285418
|
312
433
|
def to_f
|
313
434
|
utc.to_f
|
314
435
|
end
|
315
436
|
|
437
|
+
# Returns the object's date and time as an integer number of seconds
|
438
|
+
# since the Epoch (January 1, 1970 00:00 UTC).
|
439
|
+
#
|
440
|
+
# Time.zone.now.to_i # => 1417709320
|
316
441
|
def to_i
|
317
442
|
utc.to_i
|
318
443
|
end
|
319
444
|
alias_method :tv_sec, :to_i
|
320
445
|
|
446
|
+
# Returns the object's date and time as a rational number of seconds
|
447
|
+
# since the Epoch (January 1, 1970 00:00 UTC).
|
448
|
+
#
|
449
|
+
# Time.zone.now.to_r # => (708854548642709/500000)
|
321
450
|
def to_r
|
322
451
|
utc.to_r
|
323
452
|
end
|
324
453
|
|
454
|
+
# Returns an instance of DateTime with the timezone's UTC offset
|
455
|
+
#
|
456
|
+
# Time.zone.now.to_datetime # => Tue, 18 Aug 2015 02:32:20 +0000
|
457
|
+
# Time.current.in_time_zone('Hawaii').to_datetime # => Mon, 17 Aug 2015 16:32:20 -1000
|
325
458
|
def to_datetime
|
326
459
|
@to_datetime ||= utc.to_datetime.new_offset(Rational(utc_offset, 86_400))
|
327
460
|
end
|
@@ -348,6 +481,11 @@ module ActiveSupport
|
|
348
481
|
end
|
349
482
|
alias_method :kind_of?, :is_a?
|
350
483
|
|
484
|
+
# An instance of ActiveSupport::TimeWithZone is never blank
|
485
|
+
def blank?
|
486
|
+
false
|
487
|
+
end
|
488
|
+
|
351
489
|
def freeze
|
352
490
|
# preload instance variables before freezing
|
353
491
|
period; utc; time; to_datetime; to_time
|
@@ -382,7 +520,7 @@ module ActiveSupport
|
|
382
520
|
def method_missing(sym, *args, &block)
|
383
521
|
wrap_with_time_zone time.__send__(sym, *args, &block)
|
384
522
|
rescue NoMethodError => e
|
385
|
-
raise e, e.message.sub(time.inspect,
|
523
|
+
raise e, e.message.sub(time.inspect, inspect), e.backtrace
|
386
524
|
end
|
387
525
|
|
388
526
|
private
|
@@ -400,11 +538,13 @@ module ActiveSupport
|
|
400
538
|
end
|
401
539
|
|
402
540
|
def transfer_time_values_to_utc_constructor(time)
|
541
|
+
# avoid creating another Time object if possible
|
542
|
+
return time if time.instance_of?(::Time) && time.utc?
|
403
543
|
::Time.utc(time.year, time.month, time.day, time.hour, time.min, time.sec + time.subsec)
|
404
544
|
end
|
405
545
|
|
406
546
|
def duration_of_variable_length?(obj)
|
407
|
-
ActiveSupport::Duration === obj && obj.parts.any? {|p| [:years, :months, :days].include?(p[0]) }
|
547
|
+
ActiveSupport::Duration === obj && obj.parts.any? { |p| [:years, :months, :weeks, :days].include?(p[0]) }
|
408
548
|
end
|
409
549
|
|
410
550
|
def wrap_with_time_zone(time)
|