activesupport 4.2.11.1 → 5.2.8.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 +441 -399
- data/MIT-LICENSE +2 -2
- data/README.rdoc +4 -5
- data/lib/active_support/all.rb +5 -3
- data/lib/active_support/array_inquirer.rb +48 -0
- data/lib/active_support/backtrace_cleaner.rb +7 -5
- data/lib/active_support/benchmarkable.rb +6 -4
- data/lib/active_support/builder.rb +3 -1
- data/lib/active_support/cache/file_store.rb +41 -35
- data/lib/active_support/cache/mem_cache_store.rb +91 -91
- data/lib/active_support/cache/memory_store.rb +27 -30
- data/lib/active_support/cache/null_store.rb +7 -8
- data/lib/active_support/cache/redis_cache_store.rb +466 -0
- data/lib/active_support/cache/strategy/local_cache.rb +67 -34
- data/lib/active_support/cache/strategy/local_cache_middleware.rb +10 -9
- data/lib/active_support/cache.rb +287 -196
- data/lib/active_support/callbacks.rb +640 -590
- data/lib/active_support/concern.rb +11 -5
- data/lib/active_support/concurrency/load_interlock_aware_monitor.rb +35 -0
- data/lib/active_support/concurrency/share_lock.rb +227 -0
- data/lib/active_support/configurable.rb +8 -5
- data/lib/active_support/core_ext/array/access.rb +29 -1
- data/lib/active_support/core_ext/array/conversions.rb +22 -18
- 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 +5 -3
- 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 +41 -22
- 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 +11 -9
- 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 +170 -58
- 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 -12
- 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 +36 -18
- data/lib/active_support/core_ext/date_time/compatibility.rb +8 -6
- data/lib/active_support/core_ext/date_time/conversions.rb +16 -12
- 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 +101 -33
- 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 +14 -9
- 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/except.rb +11 -8
- data/lib/active_support/core_ext/hash/indifferent_access.rb +4 -3
- data/lib/active_support/core_ext/hash/keys.rb +33 -27
- data/lib/active_support/core_ext/hash/reverse_merge.rb +5 -2
- data/lib/active_support/core_ext/hash/slice.rb +8 -8
- data/lib/active_support/core_ext/hash/transform_values.rb +14 -5
- data/lib/active_support/core_ext/hash.rb +11 -9
- data/lib/active_support/core_ext/integer/inflections.rb +3 -1
- data/lib/active_support/core_ext/integer/multiple.rb +2 -0
- 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/agnostics.rb +2 -0
- 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 +6 -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 +43 -40
- data/lib/active_support/core_ext/module/attribute_accessors_per_thread.rb +150 -0
- data/lib/active_support/core_ext/module/concerning.rb +11 -12
- data/lib/active_support/core_ext/module/delegation.rb +99 -29
- data/lib/active_support/core_ext/module/deprecation.rb +4 -2
- data/lib/active_support/core_ext/module/introspection.rb +9 -9
- data/lib/active_support/core_ext/module/reachable.rb +5 -2
- data/lib/active_support/core_ext/module/redefine_method.rb +49 -0
- data/lib/active_support/core_ext/module/remove_method.rb +8 -3
- data/lib/active_support/core_ext/module.rb +14 -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 +78 -81
- data/lib/active_support/core_ext/numeric/inquiry.rb +28 -0
- data/lib/active_support/core_ext/numeric/time.rb +35 -23
- data/lib/active_support/core_ext/numeric.rb +6 -3
- data/lib/active_support/core_ext/object/acts_like.rb +12 -1
- data/lib/active_support/core_ext/object/blank.rb +27 -2
- 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 +41 -14
- 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 +49 -19
- 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 +69 -21
- 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 +61 -0
- data/lib/active_support/core_ext/range/conversions.rb +27 -7
- data/lib/active_support/core_ext/range/each.rb +19 -17
- data/lib/active_support/core_ext/range/include_range.rb +2 -22
- 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 +6 -0
- data/lib/active_support/core_ext/securerandom.rb +25 -0
- data/lib/active_support/core_ext/string/access.rb +8 -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 +6 -5
- data/lib/active_support/core_ext/string/indent.rb +6 -4
- data/lib/active_support/core_ext/string/inflections.rb +61 -24
- data/lib/active_support/core_ext/string/inquiry.rb +3 -1
- data/lib/active_support/core_ext/string/multibyte.rb +15 -7
- data/lib/active_support/core_ext/string/output_safety.rb +62 -38
- data/lib/active_support/core_ext/string/starts_ends_with.rb +2 -0
- data/lib/active_support/core_ext/string/strip.rb +4 -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 +85 -51
- 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 -8
- data/lib/active_support/core_ext.rb +3 -1
- data/lib/active_support/current_attributes.rb +195 -0
- data/lib/active_support/dependencies/autoload.rb +2 -0
- data/lib/active_support/dependencies/interlock.rb +57 -0
- data/lib/active_support/dependencies.rb +152 -161
- 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 +66 -20
- data/lib/active_support/deprecation/proxy_wrappers.rb +56 -28
- data/lib/active_support/deprecation/reporting.rb +32 -12
- data/lib/active_support/deprecation.rb +12 -9
- data/lib/active_support/descendants_tracker.rb +2 -0
- data/lib/active_support/digest.rb +20 -0
- data/lib/active_support/duration/iso8601_parser.rb +125 -0
- data/lib/active_support/duration/iso8601_serializer.rb +55 -0
- data/lib/active_support/duration.rb +314 -38
- data/lib/active_support/encrypted_configuration.rb +49 -0
- data/lib/active_support/encrypted_file.rb +99 -0
- data/lib/active_support/evented_file_update_checker.rb +205 -0
- data/lib/active_support/execution_wrapper.rb +131 -0
- data/lib/active_support/executor.rb +8 -0
- data/lib/active_support/file_update_checker.rb +63 -37
- data/lib/active_support/gem_version.rb +5 -3
- data/lib/active_support/gzip.rb +7 -5
- data/lib/active_support/hash_with_indifferent_access.rb +123 -28
- data/lib/active_support/i18n.rb +8 -6
- data/lib/active_support/i18n_railtie.rb +37 -13
- data/lib/active_support/inflections.rb +13 -11
- data/lib/active_support/inflector/inflections.rb +61 -12
- data/lib/active_support/inflector/methods.rb +163 -136
- data/lib/active_support/inflector/transliterate.rb +48 -27
- data/lib/active_support/inflector.rb +7 -5
- data/lib/active_support/json/decoding.rb +16 -13
- data/lib/active_support/json/encoding.rb +11 -58
- data/lib/active_support/json.rb +4 -2
- data/lib/active_support/key_generator.rb +25 -25
- data/lib/active_support/lazy_load_hooks.rb +50 -20
- 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 +13 -10
- data/lib/active_support/logger.rb +8 -7
- data/lib/active_support/logger_silence.rb +6 -4
- data/lib/active_support/logger_thread_safe_level.rb +7 -5
- data/lib/active_support/message_encryptor.rb +168 -53
- data/lib/active_support/message_verifier.rb +150 -17
- data/lib/active_support/messages/metadata.rb +71 -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 +36 -23
- data/lib/active_support/multibyte/unicode.rb +100 -96
- data/lib/active_support/multibyte.rb +4 -2
- data/lib/active_support/notifications/fanout.rb +11 -9
- data/lib/active_support/notifications/instrumenter.rb +27 -7
- data/lib/active_support/notifications.rb +11 -7
- data/lib/active_support/number_helper/number_converter.rb +13 -11
- data/lib/active_support/number_helper/number_to_currency_converter.rb +9 -9
- data/lib/active_support/number_helper/number_to_delimited_converter.rb +9 -3
- data/lib/active_support/number_helper/number_to_human_converter.rb +11 -9
- data/lib/active_support/number_helper/number_to_human_size_converter.rb +9 -8
- data/lib/active_support/number_helper/number_to_percentage_converter.rb +3 -1
- data/lib/active_support/number_helper/number_to_phone_converter.rb +13 -4
- data/lib/active_support/number_helper/number_to_rounded_converter.rb +23 -56
- data/lib/active_support/number_helper/rounding_helper.rb +66 -0
- data/lib/active_support/number_helper.rb +94 -68
- data/lib/active_support/option_merger.rb +3 -1
- data/lib/active_support/ordered_hash.rb +6 -4
- data/lib/active_support/ordered_options.rb +23 -5
- 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 +16 -8
- data/lib/active_support/railtie.rb +43 -9
- data/lib/active_support/reloader.rb +131 -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 -3
- data/lib/active_support/subscriber.rb +21 -16
- data/lib/active_support/tagged_logging.rb +14 -11
- data/lib/active_support/test_case.rb +19 -47
- data/lib/active_support/testing/assertions.rb +137 -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 +14 -10
- data/lib/active_support/testing/file_fixtures.rb +36 -0
- data/lib/active_support/testing/isolation.rb +34 -25
- data/lib/active_support/testing/method_call_assertions.rb +43 -0
- data/lib/active_support/testing/setup_and_teardown.rb +13 -8
- data/lib/active_support/testing/stream.rb +44 -0
- data/lib/active_support/testing/tagged_logging.rb +3 -1
- data/lib/active_support/testing/time_helpers.rb +81 -15
- data/lib/active_support/time.rb +14 -12
- data/lib/active_support/time_with_zone.rb +169 -39
- data/lib/active_support/values/time_zone.rb +196 -61
- data/lib/active_support/values/unicode_tables.dat +0 -0
- data/lib/active_support/version.rb +3 -1
- data/lib/active_support/xml_mini/jdom.rb +116 -114
- 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 +37 -37
- data/lib/active_support.rb +12 -11
- metadata +57 -27
- 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/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
@@ -1,5 +1,7 @@
|
|
1
|
-
|
2
|
-
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "active_support/core_ext/hash/keys"
|
4
|
+
require "active_support/core_ext/hash/reverse_merge"
|
3
5
|
|
4
6
|
module ActiveSupport
|
5
7
|
# Implements a hash where keys <tt>:foo</tt> and <tt>"foo"</tt> are considered
|
@@ -40,6 +42,12 @@ module ActiveSupport
|
|
40
42
|
# rgb = { black: '#000000', white: '#FFFFFF' }.with_indifferent_access
|
41
43
|
#
|
42
44
|
# which may be handy.
|
45
|
+
#
|
46
|
+
# To access this class outside of Rails, require the core extension with:
|
47
|
+
#
|
48
|
+
# require "active_support/core_ext/hash/indifferent_access"
|
49
|
+
#
|
50
|
+
# which will, in turn, require this file.
|
43
51
|
class HashWithIndifferentAccess < Hash
|
44
52
|
# Returns +true+ so that <tt>Array#extract_options!</tt> finds members of
|
45
53
|
# this class.
|
@@ -59,24 +67,12 @@ module ActiveSupport
|
|
59
67
|
if constructor.respond_to?(:to_hash)
|
60
68
|
super()
|
61
69
|
update(constructor)
|
62
|
-
else
|
63
|
-
super(constructor)
|
64
|
-
end
|
65
|
-
end
|
66
70
|
|
67
|
-
|
68
|
-
|
69
|
-
self
|
71
|
+
hash = constructor.to_hash
|
72
|
+
self.default = hash.default if hash.default
|
73
|
+
self.default_proc = hash.default_proc if hash.default_proc
|
70
74
|
else
|
71
|
-
super
|
72
|
-
end
|
73
|
-
end
|
74
|
-
|
75
|
-
def self.new_from_hash_copying_default(hash)
|
76
|
-
hash = hash.to_hash
|
77
|
-
new(hash).tap do |new_hash|
|
78
|
-
new_hash.default = hash.default
|
79
|
-
new_hash.default_proc = hash.default_proc if hash.default_proc
|
75
|
+
super(constructor)
|
80
76
|
end
|
81
77
|
end
|
82
78
|
|
@@ -92,7 +88,7 @@ module ActiveSupport
|
|
92
88
|
# hash = ActiveSupport::HashWithIndifferentAccess.new
|
93
89
|
# hash[:key] = 'value'
|
94
90
|
#
|
95
|
-
# This value can be later fetched using either +:key+ or
|
91
|
+
# This value can be later fetched using either +:key+ or <tt>'key'</tt>.
|
96
92
|
def []=(key, value)
|
97
93
|
regular_writer(convert_key(key), convert_value(value, for: :assignment))
|
98
94
|
end
|
@@ -154,6 +150,32 @@ module ActiveSupport
|
|
154
150
|
alias_method :has_key?, :key?
|
155
151
|
alias_method :member?, :key?
|
156
152
|
|
153
|
+
# Same as <tt>Hash#[]</tt> where the key passed as argument can be
|
154
|
+
# either a string or a symbol:
|
155
|
+
#
|
156
|
+
# counters = ActiveSupport::HashWithIndifferentAccess.new
|
157
|
+
# counters[:foo] = 1
|
158
|
+
#
|
159
|
+
# counters['foo'] # => 1
|
160
|
+
# counters[:foo] # => 1
|
161
|
+
# counters[:zoo] # => nil
|
162
|
+
def [](key)
|
163
|
+
super(convert_key(key))
|
164
|
+
end
|
165
|
+
|
166
|
+
# Same as <tt>Hash#assoc</tt> where the key passed as argument can be
|
167
|
+
# either a string or a symbol:
|
168
|
+
#
|
169
|
+
# counters = ActiveSupport::HashWithIndifferentAccess.new
|
170
|
+
# counters[:foo] = 1
|
171
|
+
#
|
172
|
+
# counters.assoc('foo') # => ["foo", 1]
|
173
|
+
# counters.assoc(:foo) # => ["foo", 1]
|
174
|
+
# counters.assoc(:zoo) # => nil
|
175
|
+
def assoc(key)
|
176
|
+
super(convert_key(key))
|
177
|
+
end
|
178
|
+
|
157
179
|
# Same as <tt>Hash#fetch</tt> where the key passed as argument can be
|
158
180
|
# either a string or a symbol:
|
159
181
|
#
|
@@ -168,6 +190,36 @@ module ActiveSupport
|
|
168
190
|
super(convert_key(key), *extras)
|
169
191
|
end
|
170
192
|
|
193
|
+
if Hash.new.respond_to?(:dig)
|
194
|
+
# Same as <tt>Hash#dig</tt> where the key passed as argument can be
|
195
|
+
# either a string or a symbol:
|
196
|
+
#
|
197
|
+
# counters = ActiveSupport::HashWithIndifferentAccess.new
|
198
|
+
# counters[:foo] = { bar: 1 }
|
199
|
+
#
|
200
|
+
# counters.dig('foo', 'bar') # => 1
|
201
|
+
# counters.dig(:foo, :bar) # => 1
|
202
|
+
# counters.dig(:zoo) # => nil
|
203
|
+
def dig(*args)
|
204
|
+
args[0] = convert_key(args[0]) if args.size > 0
|
205
|
+
super(*args)
|
206
|
+
end
|
207
|
+
end
|
208
|
+
|
209
|
+
# Same as <tt>Hash#default</tt> where the key passed as argument can be
|
210
|
+
# either a string or a symbol:
|
211
|
+
#
|
212
|
+
# hash = ActiveSupport::HashWithIndifferentAccess.new(1)
|
213
|
+
# hash.default # => 1
|
214
|
+
#
|
215
|
+
# hash = ActiveSupport::HashWithIndifferentAccess.new { |hash, key| key }
|
216
|
+
# hash.default # => nil
|
217
|
+
# hash.default('foo') # => 'foo'
|
218
|
+
# hash.default(:foo) # => 'foo'
|
219
|
+
def default(*args)
|
220
|
+
super(*args.map { |arg| convert_key(arg) })
|
221
|
+
end
|
222
|
+
|
171
223
|
# Returns an array of the values at the specified indices:
|
172
224
|
#
|
173
225
|
# hash = ActiveSupport::HashWithIndifferentAccess.new
|
@@ -178,13 +230,26 @@ module ActiveSupport
|
|
178
230
|
indices.collect { |key| self[convert_key(key)] }
|
179
231
|
end
|
180
232
|
|
233
|
+
# Returns an array of the values at the specified indices, but also
|
234
|
+
# raises an exception when one of the keys can't be found.
|
235
|
+
#
|
236
|
+
# hash = ActiveSupport::HashWithIndifferentAccess.new
|
237
|
+
# hash[:a] = 'x'
|
238
|
+
# hash[:b] = 'y'
|
239
|
+
# hash.fetch_values('a', 'b') # => ["x", "y"]
|
240
|
+
# hash.fetch_values('a', 'c') { |key| 'z' } # => ["x", "z"]
|
241
|
+
# hash.fetch_values('a', 'c') # => KeyError: key not found: "c"
|
242
|
+
def fetch_values(*indices, &block)
|
243
|
+
indices.collect { |key| fetch(key, &block) }
|
244
|
+
end if Hash.method_defined?(:fetch_values)
|
245
|
+
|
181
246
|
# Returns a shallow copy of the hash.
|
182
247
|
#
|
183
248
|
# hash = ActiveSupport::HashWithIndifferentAccess.new({ a: { b: 'b' } })
|
184
249
|
# dup = hash.dup
|
185
250
|
# dup[:a][:c] = 'c'
|
186
251
|
#
|
187
|
-
# hash[:a][:c] # =>
|
252
|
+
# hash[:a][:c] # => "c"
|
188
253
|
# dup[:a][:c] # => "c"
|
189
254
|
def dup
|
190
255
|
self.class.new(self).tap do |new_hash|
|
@@ -196,7 +261,7 @@ module ActiveSupport
|
|
196
261
|
# modify the receiver but rather returns a new hash with indifferent
|
197
262
|
# access with the result of the merge.
|
198
263
|
def merge(hash, &block)
|
199
|
-
|
264
|
+
dup.update(hash, &block)
|
200
265
|
end
|
201
266
|
|
202
267
|
# Like +merge+ but the other way around: Merges the receiver into the
|
@@ -206,20 +271,22 @@ module ActiveSupport
|
|
206
271
|
# hash['a'] = nil
|
207
272
|
# hash.reverse_merge(a: 0, b: 1) # => {"a"=>nil, "b"=>1}
|
208
273
|
def reverse_merge(other_hash)
|
209
|
-
super(self.class.
|
274
|
+
super(self.class.new(other_hash))
|
210
275
|
end
|
276
|
+
alias_method :with_defaults, :reverse_merge
|
211
277
|
|
212
278
|
# Same semantics as +reverse_merge+ but modifies the receiver in-place.
|
213
279
|
def reverse_merge!(other_hash)
|
214
|
-
|
280
|
+
super(self.class.new(other_hash))
|
215
281
|
end
|
282
|
+
alias_method :with_defaults!, :reverse_merge!
|
216
283
|
|
217
284
|
# Replaces the contents of this hash with other_hash.
|
218
285
|
#
|
219
286
|
# h = { "a" => 100, "b" => 200 }
|
220
287
|
# h.replace({ "c" => 300, "d" => 400 }) # => {"c"=>300, "d"=>400}
|
221
288
|
def replace(other_hash)
|
222
|
-
super(self.class.
|
289
|
+
super(self.class.new(other_hash))
|
223
290
|
end
|
224
291
|
|
225
292
|
# Removes the specified key from the hash.
|
@@ -234,14 +301,17 @@ module ActiveSupport
|
|
234
301
|
undef :symbolize_keys!
|
235
302
|
undef :deep_symbolize_keys!
|
236
303
|
def symbolize_keys; to_hash.symbolize_keys! end
|
304
|
+
alias_method :to_options, :symbolize_keys
|
237
305
|
def deep_symbolize_keys; to_hash.deep_symbolize_keys! end
|
238
306
|
def to_options!; self end
|
239
307
|
|
240
308
|
def select(*args, &block)
|
309
|
+
return to_enum(:select) unless block_given?
|
241
310
|
dup.tap { |hash| hash.select!(*args, &block) }
|
242
311
|
end
|
243
312
|
|
244
313
|
def reject(*args, &block)
|
314
|
+
return to_enum(:reject) unless block_given?
|
245
315
|
dup.tap { |hash| hash.reject!(*args, &block) }
|
246
316
|
end
|
247
317
|
|
@@ -250,6 +320,29 @@ module ActiveSupport
|
|
250
320
|
dup.tap { |hash| hash.transform_values!(*args, &block) }
|
251
321
|
end
|
252
322
|
|
323
|
+
def transform_keys(*args, &block)
|
324
|
+
return to_enum(:transform_keys) unless block_given?
|
325
|
+
dup.tap { |hash| hash.transform_keys!(*args, &block) }
|
326
|
+
end
|
327
|
+
|
328
|
+
def transform_keys!
|
329
|
+
return enum_for(:transform_keys!) { size } unless block_given?
|
330
|
+
keys.each do |key|
|
331
|
+
self[yield(key)] = delete(key)
|
332
|
+
end
|
333
|
+
self
|
334
|
+
end
|
335
|
+
|
336
|
+
def slice(*keys)
|
337
|
+
keys.map! { |key| convert_key(key) }
|
338
|
+
self.class.new(super)
|
339
|
+
end
|
340
|
+
|
341
|
+
def slice!(*keys)
|
342
|
+
keys.map! { |key| convert_key(key) }
|
343
|
+
super
|
344
|
+
end
|
345
|
+
|
253
346
|
def compact
|
254
347
|
dup.tap(&:compact!)
|
255
348
|
end
|
@@ -265,12 +358,12 @@ module ActiveSupport
|
|
265
358
|
_new_hash
|
266
359
|
end
|
267
360
|
|
268
|
-
|
269
|
-
def convert_key(key)
|
361
|
+
private
|
362
|
+
def convert_key(key) # :doc:
|
270
363
|
key.kind_of?(Symbol) ? key.to_s : key
|
271
364
|
end
|
272
365
|
|
273
|
-
def convert_value(value, options = {})
|
366
|
+
def convert_value(value, options = {}) # :doc:
|
274
367
|
if value.is_a? Hash
|
275
368
|
if options[:for] == :to_hash
|
276
369
|
value.to_hash
|
@@ -287,7 +380,7 @@ module ActiveSupport
|
|
287
380
|
end
|
288
381
|
end
|
289
382
|
|
290
|
-
def set_defaults(target)
|
383
|
+
def set_defaults(target) # :doc:
|
291
384
|
if default_proc
|
292
385
|
target.default_proc = default_proc.dup
|
293
386
|
else
|
@@ -297,4 +390,6 @@ module ActiveSupport
|
|
297
390
|
end
|
298
391
|
end
|
299
392
|
|
393
|
+
# :stopdoc:
|
394
|
+
|
300
395
|
HashWithIndifferentAccess = ActiveSupport::HashWithIndifferentAccess
|
data/lib/active_support/i18n.rb
CHANGED
@@ -1,13 +1,15 @@
|
|
1
|
-
|
2
|
-
|
3
|
-
require
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "active_support/core_ext/hash/deep_merge"
|
4
|
+
require "active_support/core_ext/hash/except"
|
5
|
+
require "active_support/core_ext/hash/slice"
|
4
6
|
begin
|
5
|
-
require
|
7
|
+
require "i18n"
|
6
8
|
rescue LoadError => e
|
7
9
|
$stderr.puts "The i18n gem is not available. Please add it to your Gemfile and run bundle install"
|
8
10
|
raise e
|
9
11
|
end
|
10
|
-
require
|
12
|
+
require "active_support/lazy_load_hooks"
|
11
13
|
|
12
14
|
ActiveSupport.run_load_hooks(:i18n)
|
13
|
-
I18n.load_path <<
|
15
|
+
I18n.load_path << File.expand_path("locale/en.yml", __dir__)
|
@@ -1,7 +1,11 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
require "active_support"
|
2
4
|
require "active_support/file_update_checker"
|
3
5
|
require "active_support/core_ext/array/wrap"
|
4
6
|
|
7
|
+
# :enddoc:
|
8
|
+
|
5
9
|
module I18n
|
6
10
|
class Railtie < Rails::Railtie
|
7
11
|
config.i18n = ActiveSupport::OrderedOptions.new
|
@@ -21,8 +25,6 @@ module I18n
|
|
21
25
|
I18n::Railtie.initialize_i18n(app)
|
22
26
|
end
|
23
27
|
|
24
|
-
protected
|
25
|
-
|
26
28
|
@i18n_inited = false
|
27
29
|
|
28
30
|
# Setup i18n configuration.
|
@@ -37,10 +39,12 @@ module I18n
|
|
37
39
|
enforce_available_locales = I18n.enforce_available_locales if enforce_available_locales.nil?
|
38
40
|
I18n.enforce_available_locales = false
|
39
41
|
|
42
|
+
reloadable_paths = []
|
40
43
|
app.config.i18n.each do |setting, value|
|
41
44
|
case setting
|
42
45
|
when :railties_load_path
|
43
|
-
|
46
|
+
reloadable_paths = value
|
47
|
+
app.config.i18n.load_path.unshift(*value.flat_map(&:existent))
|
44
48
|
when :load_path
|
45
49
|
I18n.load_path += value
|
46
50
|
else
|
@@ -53,28 +57,42 @@ module I18n
|
|
53
57
|
# Restore available locales check so it will take place from now on.
|
54
58
|
I18n.enforce_available_locales = enforce_available_locales
|
55
59
|
|
56
|
-
|
60
|
+
directories = watched_dirs_with_extensions(reloadable_paths)
|
61
|
+
reloader = app.config.file_watcher.new(I18n.load_path.dup, directories) do
|
62
|
+
I18n.load_path.keep_if { |p| File.exist?(p) }
|
63
|
+
I18n.load_path |= reloadable_paths.flat_map(&:existent)
|
64
|
+
|
65
|
+
I18n.reload!
|
66
|
+
end
|
67
|
+
|
57
68
|
app.reloaders << reloader
|
58
|
-
|
69
|
+
app.reloader.to_run do
|
70
|
+
reloader.execute_if_updated { require_unload_lock! }
|
71
|
+
end
|
59
72
|
reloader.execute
|
60
73
|
|
61
74
|
@i18n_inited = true
|
62
75
|
end
|
63
76
|
|
64
77
|
def self.include_fallbacks_module
|
65
|
-
I18n.backend.class.
|
78
|
+
I18n.backend.class.include(I18n::Backend::Fallbacks)
|
66
79
|
end
|
67
80
|
|
68
81
|
def self.init_fallbacks(fallbacks)
|
69
82
|
include_fallbacks_module
|
70
83
|
|
71
|
-
args =
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
Array
|
76
|
-
|
77
|
-
|
84
|
+
args = \
|
85
|
+
case fallbacks
|
86
|
+
when ActiveSupport::OrderedOptions
|
87
|
+
[*(fallbacks[:defaults] || []) << fallbacks[:map]].compact
|
88
|
+
when Hash, Array
|
89
|
+
Array.wrap(fallbacks)
|
90
|
+
else # TrueClass
|
91
|
+
[I18n.default_locale]
|
92
|
+
end
|
93
|
+
|
94
|
+
if args.empty? || args.first.is_a?(Hash)
|
95
|
+
args.unshift I18n.default_locale
|
78
96
|
end
|
79
97
|
|
80
98
|
I18n.fallbacks = I18n::Locale::Fallbacks.new(*args)
|
@@ -90,5 +108,11 @@ module I18n
|
|
90
108
|
raise "Unexpected fallback type #{fallbacks.inspect}"
|
91
109
|
end
|
92
110
|
end
|
111
|
+
|
112
|
+
def self.watched_dirs_with_extensions(paths)
|
113
|
+
paths.each_with_object({}) do |path, result|
|
114
|
+
result[path.absolute_current] = path.extensions
|
115
|
+
end
|
116
|
+
end
|
93
117
|
end
|
94
118
|
end
|
@@ -1,4 +1,6 @@
|
|
1
|
-
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "active_support/inflector/inflections"
|
2
4
|
|
3
5
|
#--
|
4
6
|
# Defines the standard inflection rules. These are the starting point for
|
@@ -8,8 +10,8 @@ require 'active_support/inflector/inflections'
|
|
8
10
|
#++
|
9
11
|
module ActiveSupport
|
10
12
|
Inflector.inflections(:en) do |inflect|
|
11
|
-
inflect.plural(/$/,
|
12
|
-
inflect.plural(/s$/i,
|
13
|
+
inflect.plural(/$/, "s")
|
14
|
+
inflect.plural(/s$/i, "s")
|
13
15
|
inflect.plural(/^(ax|test)is$/i, '\1es')
|
14
16
|
inflect.plural(/(octop|vir)us$/i, '\1i')
|
15
17
|
inflect.plural(/(octop|vir)i$/i, '\1i')
|
@@ -18,7 +20,7 @@ module ActiveSupport
|
|
18
20
|
inflect.plural(/(buffal|tomat)o$/i, '\1oes')
|
19
21
|
inflect.plural(/([ti])um$/i, '\1a')
|
20
22
|
inflect.plural(/([ti])a$/i, '\1a')
|
21
|
-
inflect.plural(/sis$/i,
|
23
|
+
inflect.plural(/sis$/i, "ses")
|
22
24
|
inflect.plural(/(?:([^f])fe|([lr])f)$/i, '\1\2ves')
|
23
25
|
inflect.plural(/(hive)$/i, '\1s')
|
24
26
|
inflect.plural(/([^aeiouy]|qu)y$/i, '\1ies')
|
@@ -30,7 +32,7 @@ module ActiveSupport
|
|
30
32
|
inflect.plural(/^(oxen)$/i, '\1')
|
31
33
|
inflect.plural(/(quiz)$/i, '\1zes')
|
32
34
|
|
33
|
-
inflect.singular(/s$/i,
|
35
|
+
inflect.singular(/s$/i, "")
|
34
36
|
inflect.singular(/(ss)$/i, '\1')
|
35
37
|
inflect.singular(/(n)ews$/i, '\1ews')
|
36
38
|
inflect.singular(/([ti])a$/i, '\1um')
|
@@ -58,12 +60,12 @@ module ActiveSupport
|
|
58
60
|
inflect.singular(/(quiz)zes$/i, '\1')
|
59
61
|
inflect.singular(/(database)s$/i, '\1')
|
60
62
|
|
61
|
-
inflect.irregular(
|
62
|
-
inflect.irregular(
|
63
|
-
inflect.irregular(
|
64
|
-
inflect.irregular(
|
65
|
-
inflect.irregular(
|
66
|
-
inflect.irregular(
|
63
|
+
inflect.irregular("person", "people")
|
64
|
+
inflect.irregular("man", "men")
|
65
|
+
inflect.irregular("child", "children")
|
66
|
+
inflect.irregular("sex", "sexes")
|
67
|
+
inflect.irregular("move", "moves")
|
68
|
+
inflect.irregular("zombie", "zombies")
|
67
69
|
|
68
70
|
inflect.uncountable(%w(equipment information rice money species series fish sheep jeans police))
|
69
71
|
end
|
@@ -1,6 +1,10 @@
|
|
1
|
-
|
2
|
-
|
3
|
-
require
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "concurrent/map"
|
4
|
+
require "active_support/core_ext/array/prepend_and_append"
|
5
|
+
require "active_support/core_ext/regexp"
|
6
|
+
require "active_support/i18n"
|
7
|
+
require "active_support/deprecation"
|
4
8
|
|
5
9
|
module ActiveSupport
|
6
10
|
module Inflector
|
@@ -25,23 +29,60 @@ module ActiveSupport
|
|
25
29
|
# singularization rules that is runs. This guarantees that your rules run
|
26
30
|
# before any of the rules that may already have been loaded.
|
27
31
|
class Inflections
|
28
|
-
@__instance__ =
|
32
|
+
@__instance__ = Concurrent::Map.new
|
33
|
+
|
34
|
+
class Uncountables < Array
|
35
|
+
def initialize
|
36
|
+
@regex_array = []
|
37
|
+
super
|
38
|
+
end
|
39
|
+
|
40
|
+
def delete(entry)
|
41
|
+
super entry
|
42
|
+
@regex_array.delete(to_regex(entry))
|
43
|
+
end
|
44
|
+
|
45
|
+
def <<(*word)
|
46
|
+
add(word)
|
47
|
+
end
|
48
|
+
|
49
|
+
def add(words)
|
50
|
+
words = words.flatten.map(&:downcase)
|
51
|
+
concat(words)
|
52
|
+
@regex_array += words.map { |word| to_regex(word) }
|
53
|
+
self
|
54
|
+
end
|
55
|
+
|
56
|
+
def uncountable?(str)
|
57
|
+
@regex_array.any? { |regex| regex.match? str }
|
58
|
+
end
|
59
|
+
|
60
|
+
private
|
61
|
+
def to_regex(string)
|
62
|
+
/\b#{::Regexp.escape(string)}\Z/i
|
63
|
+
end
|
64
|
+
end
|
29
65
|
|
30
66
|
def self.instance(locale = :en)
|
31
67
|
@__instance__[locale] ||= new
|
32
68
|
end
|
33
69
|
|
34
70
|
attr_reader :plurals, :singulars, :uncountables, :humans, :acronyms, :acronym_regex
|
71
|
+
deprecate :acronym_regex
|
72
|
+
|
73
|
+
attr_reader :acronyms_camelize_regex, :acronyms_underscore_regex # :nodoc:
|
35
74
|
|
36
75
|
def initialize
|
37
|
-
@plurals, @singulars, @uncountables, @humans, @acronyms
|
76
|
+
@plurals, @singulars, @uncountables, @humans, @acronyms = [], [], Uncountables.new, [], {}
|
77
|
+
define_acronym_regex_patterns
|
38
78
|
end
|
39
79
|
|
40
80
|
# Private, for the test suite.
|
41
81
|
def initialize_dup(orig) # :nodoc:
|
42
|
-
%w(plurals singulars uncountables humans acronyms
|
82
|
+
%w(plurals singulars uncountables humans acronyms).each do |scope|
|
43
83
|
instance_variable_set("@#{scope}", orig.send(scope).dup)
|
44
84
|
end
|
85
|
+
define_acronym_regex_patterns
|
45
86
|
end
|
46
87
|
|
47
88
|
# Specifies a new acronym. An acronym must be specified as it will appear
|
@@ -95,7 +136,7 @@ module ActiveSupport
|
|
95
136
|
# camelize 'mcdonald' # => 'McDonald'
|
96
137
|
def acronym(word)
|
97
138
|
@acronyms[word.downcase] = word
|
98
|
-
|
139
|
+
define_acronym_regex_patterns
|
99
140
|
end
|
100
141
|
|
101
142
|
# Specifies a new pluralization rule and its replacement. The rule can
|
@@ -160,7 +201,7 @@ module ActiveSupport
|
|
160
201
|
# uncountable 'money', 'information'
|
161
202
|
# uncountable %w( money information rice )
|
162
203
|
def uncountable(*words)
|
163
|
-
@uncountables
|
204
|
+
@uncountables.add(words)
|
164
205
|
end
|
165
206
|
|
166
207
|
# Specifies a humanized form of a string by a regular expression rule or
|
@@ -184,12 +225,20 @@ module ActiveSupport
|
|
184
225
|
# clear :plurals
|
185
226
|
def clear(scope = :all)
|
186
227
|
case scope
|
187
|
-
|
188
|
-
|
189
|
-
|
190
|
-
|
228
|
+
when :all
|
229
|
+
@plurals, @singulars, @uncountables, @humans = [], [], Uncountables.new, []
|
230
|
+
else
|
231
|
+
instance_variable_set "@#{scope}", []
|
191
232
|
end
|
192
233
|
end
|
234
|
+
|
235
|
+
private
|
236
|
+
|
237
|
+
def define_acronym_regex_patterns
|
238
|
+
@acronym_regex = @acronyms.empty? ? /(?=a)b/ : /#{@acronyms.values.join("|")}/
|
239
|
+
@acronyms_camelize_regex = /^(?:#{@acronym_regex}(?=\b|[A-Z_])|\w)/
|
240
|
+
@acronyms_underscore_regex = /(?:(?<=([A-Za-z\d]))|\b)(#{@acronym_regex})(?=\b|[^a-z])/
|
241
|
+
end
|
193
242
|
end
|
194
243
|
|
195
244
|
# Yields a singleton instance of Inflector::Inflections so you can specify
|