activesupport 4.2.8 → 5.2.6

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.

Files changed (256) hide show
  1. checksums.yaml +5 -5
  2. data/CHANGELOG.md +424 -373
  3. data/MIT-LICENSE +2 -2
  4. data/README.rdoc +4 -5
  5. data/lib/active_support/all.rb +5 -3
  6. data/lib/active_support/array_inquirer.rb +48 -0
  7. data/lib/active_support/backtrace_cleaner.rb +7 -5
  8. data/lib/active_support/benchmarkable.rb +6 -4
  9. data/lib/active_support/builder.rb +3 -1
  10. data/lib/active_support/cache/file_store.rb +41 -35
  11. data/lib/active_support/cache/mem_cache_store.rb +91 -91
  12. data/lib/active_support/cache/memory_store.rb +27 -30
  13. data/lib/active_support/cache/null_store.rb +7 -8
  14. data/lib/active_support/cache/redis_cache_store.rb +466 -0
  15. data/lib/active_support/cache/strategy/local_cache.rb +67 -34
  16. data/lib/active_support/cache/strategy/local_cache_middleware.rb +10 -9
  17. data/lib/active_support/cache.rb +287 -196
  18. data/lib/active_support/callbacks.rb +640 -590
  19. data/lib/active_support/concern.rb +11 -5
  20. data/lib/active_support/concurrency/load_interlock_aware_monitor.rb +17 -0
  21. data/lib/active_support/concurrency/share_lock.rb +227 -0
  22. data/lib/active_support/configurable.rb +8 -5
  23. data/lib/active_support/core_ext/array/access.rb +29 -1
  24. data/lib/active_support/core_ext/array/conversions.rb +22 -18
  25. data/lib/active_support/core_ext/array/extract_options.rb +2 -0
  26. data/lib/active_support/core_ext/array/grouping.rb +11 -18
  27. data/lib/active_support/core_ext/array/inquiry.rb +19 -0
  28. data/lib/active_support/core_ext/array/prepend_and_append.rb +5 -3
  29. data/lib/active_support/core_ext/array/wrap.rb +7 -4
  30. data/lib/active_support/core_ext/array.rb +9 -6
  31. data/lib/active_support/core_ext/benchmark.rb +3 -1
  32. data/lib/active_support/core_ext/big_decimal/conversions.rb +10 -12
  33. data/lib/active_support/core_ext/big_decimal.rb +3 -1
  34. data/lib/active_support/core_ext/class/attribute.rb +41 -22
  35. data/lib/active_support/core_ext/class/attribute_accessors.rb +3 -1
  36. data/lib/active_support/core_ext/class/subclasses.rb +20 -6
  37. data/lib/active_support/core_ext/class.rb +4 -3
  38. data/lib/active_support/core_ext/date/acts_like.rb +3 -1
  39. data/lib/active_support/core_ext/date/blank.rb +14 -0
  40. data/lib/active_support/core_ext/date/calculations.rb +11 -9
  41. data/lib/active_support/core_ext/date/conversions.rb +25 -23
  42. data/lib/active_support/core_ext/date/zones.rb +4 -2
  43. data/lib/active_support/core_ext/date.rb +6 -4
  44. data/lib/active_support/core_ext/date_and_time/calculations.rb +170 -58
  45. data/lib/active_support/core_ext/date_and_time/compatibility.rb +4 -17
  46. data/lib/active_support/core_ext/date_and_time/zones.rb +12 -12
  47. data/lib/active_support/core_ext/date_time/acts_like.rb +4 -2
  48. data/lib/active_support/core_ext/date_time/blank.rb +14 -0
  49. data/lib/active_support/core_ext/date_time/calculations.rb +29 -16
  50. data/lib/active_support/core_ext/date_time/compatibility.rb +14 -1
  51. data/lib/active_support/core_ext/date_time/conversions.rb +16 -12
  52. data/lib/active_support/core_ext/date_time.rb +7 -5
  53. data/lib/active_support/core_ext/digest/uuid.rb +7 -5
  54. data/lib/active_support/core_ext/digest.rb +3 -0
  55. data/lib/active_support/core_ext/enumerable.rb +101 -33
  56. data/lib/active_support/core_ext/file/atomic.rb +38 -31
  57. data/lib/active_support/core_ext/file.rb +3 -1
  58. data/lib/active_support/core_ext/hash/compact.rb +14 -9
  59. data/lib/active_support/core_ext/hash/conversions.rb +62 -41
  60. data/lib/active_support/core_ext/hash/deep_merge.rb +9 -13
  61. data/lib/active_support/core_ext/hash/except.rb +11 -8
  62. data/lib/active_support/core_ext/hash/indifferent_access.rb +4 -3
  63. data/lib/active_support/core_ext/hash/keys.rb +33 -27
  64. data/lib/active_support/core_ext/hash/reverse_merge.rb +5 -2
  65. data/lib/active_support/core_ext/hash/slice.rb +8 -8
  66. data/lib/active_support/core_ext/hash/transform_values.rb +14 -5
  67. data/lib/active_support/core_ext/hash.rb +11 -9
  68. data/lib/active_support/core_ext/integer/inflections.rb +3 -1
  69. data/lib/active_support/core_ext/integer/multiple.rb +2 -0
  70. data/lib/active_support/core_ext/integer/time.rb +11 -18
  71. data/lib/active_support/core_ext/integer.rb +5 -3
  72. data/lib/active_support/core_ext/kernel/agnostics.rb +2 -0
  73. data/lib/active_support/core_ext/kernel/concern.rb +5 -1
  74. data/lib/active_support/core_ext/kernel/reporting.rb +4 -84
  75. data/lib/active_support/core_ext/kernel/singleton_class.rb +2 -0
  76. data/lib/active_support/core_ext/kernel.rb +6 -5
  77. data/lib/active_support/core_ext/load_error.rb +3 -22
  78. data/lib/active_support/core_ext/marshal.rb +8 -8
  79. data/lib/active_support/core_ext/module/aliasing.rb +6 -44
  80. data/lib/active_support/core_ext/module/anonymous.rb +12 -1
  81. data/lib/active_support/core_ext/module/attr_internal.rb +8 -9
  82. data/lib/active_support/core_ext/module/attribute_accessors.rb +43 -40
  83. data/lib/active_support/core_ext/module/attribute_accessors_per_thread.rb +150 -0
  84. data/lib/active_support/core_ext/module/concerning.rb +11 -12
  85. data/lib/active_support/core_ext/module/delegation.rb +99 -29
  86. data/lib/active_support/core_ext/module/deprecation.rb +4 -2
  87. data/lib/active_support/core_ext/module/introspection.rb +9 -9
  88. data/lib/active_support/core_ext/module/reachable.rb +5 -2
  89. data/lib/active_support/core_ext/module/redefine_method.rb +49 -0
  90. data/lib/active_support/core_ext/module/remove_method.rb +8 -3
  91. data/lib/active_support/core_ext/module.rb +14 -11
  92. data/lib/active_support/core_ext/name_error.rb +22 -2
  93. data/lib/active_support/core_ext/numeric/bytes.rb +22 -0
  94. data/lib/active_support/core_ext/numeric/conversions.rb +78 -81
  95. data/lib/active_support/core_ext/numeric/inquiry.rb +28 -0
  96. data/lib/active_support/core_ext/numeric/time.rb +35 -23
  97. data/lib/active_support/core_ext/numeric.rb +6 -3
  98. data/lib/active_support/core_ext/object/acts_like.rb +12 -1
  99. data/lib/active_support/core_ext/object/blank.rb +27 -2
  100. data/lib/active_support/core_ext/object/conversions.rb +6 -4
  101. data/lib/active_support/core_ext/object/deep_dup.rb +13 -4
  102. data/lib/active_support/core_ext/object/duplicable.rb +41 -14
  103. data/lib/active_support/core_ext/object/inclusion.rb +5 -3
  104. data/lib/active_support/core_ext/object/instance_variables.rb +3 -1
  105. data/lib/active_support/core_ext/object/json.rb +49 -19
  106. data/lib/active_support/core_ext/object/to_param.rb +3 -1
  107. data/lib/active_support/core_ext/object/to_query.rb +10 -5
  108. data/lib/active_support/core_ext/object/try.rb +69 -21
  109. data/lib/active_support/core_ext/object/with_options.rb +16 -3
  110. data/lib/active_support/core_ext/object.rb +14 -13
  111. data/lib/active_support/core_ext/range/compare_range.rb +61 -0
  112. data/lib/active_support/core_ext/range/conversions.rb +27 -7
  113. data/lib/active_support/core_ext/range/each.rb +19 -17
  114. data/lib/active_support/core_ext/range/include_range.rb +2 -22
  115. data/lib/active_support/core_ext/range/include_time_with_zone.rb +23 -0
  116. data/lib/active_support/core_ext/range/overlaps.rb +2 -0
  117. data/lib/active_support/core_ext/range.rb +7 -4
  118. data/lib/active_support/core_ext/regexp.rb +6 -0
  119. data/lib/active_support/core_ext/securerandom.rb +25 -0
  120. data/lib/active_support/core_ext/string/access.rb +8 -6
  121. data/lib/active_support/core_ext/string/behavior.rb +3 -1
  122. data/lib/active_support/core_ext/string/conversions.rb +7 -4
  123. data/lib/active_support/core_ext/string/exclude.rb +2 -0
  124. data/lib/active_support/core_ext/string/filters.rb +6 -5
  125. data/lib/active_support/core_ext/string/indent.rb +6 -4
  126. data/lib/active_support/core_ext/string/inflections.rb +61 -24
  127. data/lib/active_support/core_ext/string/inquiry.rb +3 -1
  128. data/lib/active_support/core_ext/string/multibyte.rb +15 -7
  129. data/lib/active_support/core_ext/string/output_safety.rb +34 -38
  130. data/lib/active_support/core_ext/string/starts_ends_with.rb +2 -0
  131. data/lib/active_support/core_ext/string/strip.rb +4 -5
  132. data/lib/active_support/core_ext/string/zones.rb +4 -2
  133. data/lib/active_support/core_ext/string.rb +15 -13
  134. data/lib/active_support/core_ext/time/acts_like.rb +3 -1
  135. data/lib/active_support/core_ext/time/calculations.rb +88 -52
  136. data/lib/active_support/core_ext/time/compatibility.rb +12 -1
  137. data/lib/active_support/core_ext/time/conversions.rb +20 -13
  138. data/lib/active_support/core_ext/time/zones.rb +41 -7
  139. data/lib/active_support/core_ext/time.rb +7 -6
  140. data/lib/active_support/core_ext/uri.rb +6 -8
  141. data/lib/active_support/core_ext.rb +3 -1
  142. data/lib/active_support/current_attributes.rb +195 -0
  143. data/lib/active_support/dependencies/autoload.rb +2 -0
  144. data/lib/active_support/dependencies/interlock.rb +57 -0
  145. data/lib/active_support/dependencies.rb +152 -161
  146. data/lib/active_support/deprecation/behaviors.rb +44 -11
  147. data/lib/active_support/deprecation/constant_accessor.rb +52 -0
  148. data/lib/active_support/deprecation/instance_delegator.rb +17 -2
  149. data/lib/active_support/deprecation/method_wrappers.rb +66 -20
  150. data/lib/active_support/deprecation/proxy_wrappers.rb +56 -28
  151. data/lib/active_support/deprecation/reporting.rb +32 -12
  152. data/lib/active_support/deprecation.rb +12 -9
  153. data/lib/active_support/descendants_tracker.rb +2 -0
  154. data/lib/active_support/digest.rb +20 -0
  155. data/lib/active_support/duration/iso8601_parser.rb +125 -0
  156. data/lib/active_support/duration/iso8601_serializer.rb +55 -0
  157. data/lib/active_support/duration.rb +314 -38
  158. data/lib/active_support/encrypted_configuration.rb +49 -0
  159. data/lib/active_support/encrypted_file.rb +99 -0
  160. data/lib/active_support/evented_file_update_checker.rb +205 -0
  161. data/lib/active_support/execution_wrapper.rb +128 -0
  162. data/lib/active_support/executor.rb +8 -0
  163. data/lib/active_support/file_update_checker.rb +63 -37
  164. data/lib/active_support/gem_version.rb +5 -3
  165. data/lib/active_support/gzip.rb +7 -5
  166. data/lib/active_support/hash_with_indifferent_access.rb +127 -28
  167. data/lib/active_support/i18n.rb +8 -6
  168. data/lib/active_support/i18n_railtie.rb +37 -13
  169. data/lib/active_support/inflections.rb +13 -11
  170. data/lib/active_support/inflector/inflections.rb +61 -12
  171. data/lib/active_support/inflector/methods.rb +163 -136
  172. data/lib/active_support/inflector/transliterate.rb +48 -27
  173. data/lib/active_support/inflector.rb +7 -5
  174. data/lib/active_support/json/decoding.rb +16 -13
  175. data/lib/active_support/json/encoding.rb +11 -58
  176. data/lib/active_support/json.rb +4 -2
  177. data/lib/active_support/key_generator.rb +25 -25
  178. data/lib/active_support/lazy_load_hooks.rb +50 -20
  179. data/lib/active_support/locale/en.yml +2 -0
  180. data/lib/active_support/log_subscriber/test_helper.rb +14 -12
  181. data/lib/active_support/log_subscriber.rb +13 -10
  182. data/lib/active_support/logger.rb +19 -7
  183. data/lib/active_support/logger_silence.rb +6 -4
  184. data/lib/active_support/logger_thread_safe_level.rb +7 -5
  185. data/lib/active_support/message_encryptor.rb +168 -53
  186. data/lib/active_support/message_verifier.rb +150 -17
  187. data/lib/active_support/messages/metadata.rb +71 -0
  188. data/lib/active_support/messages/rotation_configuration.rb +22 -0
  189. data/lib/active_support/messages/rotator.rb +56 -0
  190. data/lib/active_support/multibyte/chars.rb +36 -23
  191. data/lib/active_support/multibyte/unicode.rb +100 -96
  192. data/lib/active_support/multibyte.rb +4 -2
  193. data/lib/active_support/notifications/fanout.rb +11 -9
  194. data/lib/active_support/notifications/instrumenter.rb +27 -7
  195. data/lib/active_support/notifications.rb +11 -7
  196. data/lib/active_support/number_helper/number_converter.rb +13 -11
  197. data/lib/active_support/number_helper/number_to_currency_converter.rb +9 -9
  198. data/lib/active_support/number_helper/number_to_delimited_converter.rb +9 -3
  199. data/lib/active_support/number_helper/number_to_human_converter.rb +11 -9
  200. data/lib/active_support/number_helper/number_to_human_size_converter.rb +9 -8
  201. data/lib/active_support/number_helper/number_to_percentage_converter.rb +3 -1
  202. data/lib/active_support/number_helper/number_to_phone_converter.rb +13 -4
  203. data/lib/active_support/number_helper/number_to_rounded_converter.rb +23 -56
  204. data/lib/active_support/number_helper/rounding_helper.rb +66 -0
  205. data/lib/active_support/number_helper.rb +94 -68
  206. data/lib/active_support/option_merger.rb +3 -1
  207. data/lib/active_support/ordered_hash.rb +6 -4
  208. data/lib/active_support/ordered_options.rb +23 -5
  209. data/lib/active_support/per_thread_registry.rb +9 -4
  210. data/lib/active_support/proxy_object.rb +2 -0
  211. data/lib/active_support/rails.rb +16 -8
  212. data/lib/active_support/railtie.rb +43 -9
  213. data/lib/active_support/reloader.rb +131 -0
  214. data/lib/active_support/rescuable.rb +108 -53
  215. data/lib/active_support/security_utils.rb +15 -11
  216. data/lib/active_support/string_inquirer.rb +11 -3
  217. data/lib/active_support/subscriber.rb +21 -16
  218. data/lib/active_support/tagged_logging.rb +14 -11
  219. data/lib/active_support/test_case.rb +19 -47
  220. data/lib/active_support/testing/assertions.rb +137 -20
  221. data/lib/active_support/testing/autorun.rb +4 -2
  222. data/lib/active_support/testing/constant_lookup.rb +2 -1
  223. data/lib/active_support/testing/declarative.rb +3 -1
  224. data/lib/active_support/testing/deprecation.rb +14 -10
  225. data/lib/active_support/testing/file_fixtures.rb +36 -0
  226. data/lib/active_support/testing/isolation.rb +34 -25
  227. data/lib/active_support/testing/method_call_assertions.rb +43 -0
  228. data/lib/active_support/testing/setup_and_teardown.rb +13 -8
  229. data/lib/active_support/testing/stream.rb +44 -0
  230. data/lib/active_support/testing/tagged_logging.rb +3 -1
  231. data/lib/active_support/testing/time_helpers.rb +91 -23
  232. data/lib/active_support/time.rb +14 -12
  233. data/lib/active_support/time_with_zone.rb +182 -40
  234. data/lib/active_support/values/time_zone.rb +196 -61
  235. data/lib/active_support/values/unicode_tables.dat +0 -0
  236. data/lib/active_support/version.rb +3 -1
  237. data/lib/active_support/xml_mini/jdom.rb +116 -114
  238. data/lib/active_support/xml_mini/libxml.rb +17 -16
  239. data/lib/active_support/xml_mini/libxmlsax.rb +16 -18
  240. data/lib/active_support/xml_mini/nokogiri.rb +15 -15
  241. data/lib/active_support/xml_mini/nokogirisax.rb +15 -16
  242. data/lib/active_support/xml_mini/rexml.rb +11 -9
  243. data/lib/active_support/xml_mini.rb +37 -37
  244. data/lib/active_support.rb +12 -11
  245. metadata +54 -25
  246. data/lib/active_support/concurrency/latch.rb +0 -27
  247. data/lib/active_support/core_ext/big_decimal/yaml_conversions.rb +0 -16
  248. data/lib/active_support/core_ext/class/delegating_attributes.rb +0 -45
  249. data/lib/active_support/core_ext/date_time/zones.rb +0 -6
  250. data/lib/active_support/core_ext/kernel/debugger.rb +0 -10
  251. data/lib/active_support/core_ext/module/method_transplanting.rb +0 -13
  252. data/lib/active_support/core_ext/module/qualified_const.rb +0 -52
  253. data/lib/active_support/core_ext/object/itself.rb +0 -15
  254. data/lib/active_support/core_ext/struct.rb +0 -6
  255. data/lib/active_support/core_ext/thread.rb +0 -86
  256. data/lib/active_support/core_ext/time/marshal.rb +0 -30
@@ -1,73 +1,83 @@
1
- require 'set'
2
- require 'thread'
3
- require 'thread_safe'
4
- require 'pathname'
5
- require 'active_support/core_ext/module/aliasing'
6
- require 'active_support/core_ext/module/attribute_accessors'
7
- require 'active_support/core_ext/module/introspection'
8
- require 'active_support/core_ext/module/anonymous'
9
- require 'active_support/core_ext/module/qualified_const'
10
- require 'active_support/core_ext/object/blank'
11
- require 'active_support/core_ext/kernel/reporting'
12
- require 'active_support/core_ext/load_error'
13
- require 'active_support/core_ext/name_error'
14
- require 'active_support/core_ext/string/starts_ends_with'
15
- require 'active_support/inflector'
1
+ # frozen_string_literal: true
2
+
3
+ require "set"
4
+ require "thread"
5
+ require "concurrent/map"
6
+ require "pathname"
7
+ require "active_support/core_ext/module/aliasing"
8
+ require "active_support/core_ext/module/attribute_accessors"
9
+ require "active_support/core_ext/module/introspection"
10
+ require "active_support/core_ext/module/anonymous"
11
+ require "active_support/core_ext/object/blank"
12
+ require "active_support/core_ext/kernel/reporting"
13
+ require "active_support/core_ext/load_error"
14
+ require "active_support/core_ext/name_error"
15
+ require "active_support/core_ext/string/starts_ends_with"
16
+ require "active_support/dependencies/interlock"
17
+ require "active_support/inflector"
16
18
 
17
19
  module ActiveSupport #:nodoc:
18
20
  module Dependencies #:nodoc:
19
21
  extend self
20
22
 
23
+ mattr_accessor :interlock, default: Interlock.new
24
+
25
+ # :doc:
26
+
27
+ # Execute the supplied block without interference from any
28
+ # concurrent loads.
29
+ def self.run_interlock
30
+ Dependencies.interlock.running { yield }
31
+ end
32
+
33
+ # Execute the supplied block while holding an exclusive lock,
34
+ # preventing any other thread from being inside a #run_interlock
35
+ # block at the same time.
36
+ def self.load_interlock
37
+ Dependencies.interlock.loading { yield }
38
+ end
39
+
40
+ # Execute the supplied block while holding an exclusive lock,
41
+ # preventing any other thread from being inside a #run_interlock
42
+ # block at the same time.
43
+ def self.unload_interlock
44
+ Dependencies.interlock.unloading { yield }
45
+ end
46
+
47
+ # :nodoc:
48
+
21
49
  # Should we turn on Ruby warnings on the first load of dependent files?
22
- mattr_accessor :warnings_on_first_load
23
- self.warnings_on_first_load = false
50
+ mattr_accessor :warnings_on_first_load, default: false
24
51
 
25
52
  # All files ever loaded.
26
- mattr_accessor :history
27
- self.history = Set.new
53
+ mattr_accessor :history, default: Set.new
28
54
 
29
55
  # All files currently loaded.
30
- mattr_accessor :loaded
31
- self.loaded = Set.new
56
+ mattr_accessor :loaded, default: Set.new
32
57
 
33
58
  # Stack of files being loaded.
34
- mattr_accessor :loading
35
- self.loading = []
59
+ mattr_accessor :loading, default: []
36
60
 
37
61
  # Should we load files or require them?
38
- mattr_accessor :mechanism
39
- self.mechanism = ENV['NO_RELOAD'] ? :require : :load
62
+ mattr_accessor :mechanism, default: ENV["NO_RELOAD"] ? :require : :load
40
63
 
41
64
  # The set of directories from which we may automatically load files. Files
42
65
  # under these directories will be reloaded on each request in development mode,
43
66
  # unless the directory also appears in autoload_once_paths.
44
- mattr_accessor :autoload_paths
45
- self.autoload_paths = []
67
+ mattr_accessor :autoload_paths, default: []
46
68
 
47
69
  # The set of directories from which automatically loaded constants are loaded
48
70
  # only once. All directories in this set must also be present in +autoload_paths+.
49
- mattr_accessor :autoload_once_paths
50
- self.autoload_once_paths = []
71
+ mattr_accessor :autoload_once_paths, default: []
51
72
 
52
73
  # An array of qualified constant names that have been loaded. Adding a name
53
74
  # to this array will cause it to be unloaded the next time Dependencies are
54
75
  # cleared.
55
- mattr_accessor :autoloaded_constants
56
- self.autoloaded_constants = []
76
+ mattr_accessor :autoloaded_constants, default: []
57
77
 
58
78
  # An array of constant names that need to be unloaded on every request. Used
59
79
  # to allow arbitrary constants to be marked for unloading.
60
- mattr_accessor :explicitly_unloadable_constants
61
- self.explicitly_unloadable_constants = []
62
-
63
- # The logger is used for generating information on the action run-time
64
- # (including benchmarking) if available. Can be set to nil for no logging.
65
- # Compatible with both Ruby's own Logger and Log4r loggers.
66
- mattr_accessor :logger
67
-
68
- # Set to +true+ to enable logging of const_missing and file loads.
69
- mattr_accessor :log_activity
70
- self.log_activity = false
80
+ mattr_accessor :explicitly_unloadable_constants, default: []
71
81
 
72
82
  # The WatchStack keeps a stack of the modules being watched as files are
73
83
  # loaded. If a file in the process of being loaded (parent.rb) triggers the
@@ -75,7 +85,7 @@ module ActiveSupport #:nodoc:
75
85
  # handles the new constants.
76
86
  #
77
87
  # If child.rb is being autoloaded, its constants will be added to
78
- # autoloaded_constants. If it was being `require`d, they will be discarded.
88
+ # autoloaded_constants. If it was being required, they will be discarded.
79
89
  #
80
90
  # This is handled by walking back up the watch stack and adding the constants
81
91
  # found by child.rb to the list of original constants in parent.rb.
@@ -87,9 +97,11 @@ module ActiveSupport #:nodoc:
87
97
  # parent.rb then requires namespace/child.rb, the stack will look like
88
98
  # [[Object], [Namespace]].
89
99
 
100
+ attr_reader :watching
101
+
90
102
  def initialize
91
103
  @watching = []
92
- @stack = Hash.new { |h,k| h[k] = [] }
104
+ @stack = Hash.new { |h, k| h[k] = [] }
93
105
  end
94
106
 
95
107
  def each(&block)
@@ -115,11 +127,11 @@ module ActiveSupport #:nodoc:
115
127
  next unless mod.is_a?(Module)
116
128
 
117
129
  # Get a list of the constants that were added
118
- new_constants = mod.local_constants - original_constants
130
+ new_constants = mod.constants(false) - original_constants
119
131
 
120
- # self[namespace] returns an Array of the constants that are being evaluated
132
+ # @stack[namespace] returns an Array of the constants that are being evaluated
121
133
  # for that namespace. For instance, if parent.rb requires child.rb, the first
122
- # element of self[Object] will be an Array of the constants that were present
134
+ # element of @stack[Object] will be an Array of the constants that were present
123
135
  # before parent.rb was required. The second element will be an Array of the
124
136
  # constants that were present before child.rb was required.
125
137
  @stack[namespace].each do |namespace_constants|
@@ -128,7 +140,7 @@ module ActiveSupport #:nodoc:
128
140
 
129
141
  # Normalize the list of new constants, and add them to the list we will return
130
142
  new_constants.each do |suffix|
131
- constants << ([namespace, suffix] - ["Object"]).join("::")
143
+ constants << ([namespace, suffix] - ["Object"]).join("::".freeze)
132
144
  end
133
145
  end
134
146
  constants
@@ -143,7 +155,7 @@ module ActiveSupport #:nodoc:
143
155
  @watching << namespaces.map do |namespace|
144
156
  module_name = Dependencies.to_constant_name(namespace)
145
157
  original_constants = Dependencies.qualified_const_defined?(module_name) ?
146
- Inflector.constantize(module_name).local_constants : []
158
+ Inflector.constantize(module_name).constants(false) : []
147
159
 
148
160
  @stack[module_name] << original_constants
149
161
  module_name
@@ -151,14 +163,13 @@ module ActiveSupport #:nodoc:
151
163
  end
152
164
 
153
165
  private
154
- def pop_modules(modules)
155
- modules.each { |mod| @stack[mod].pop }
156
- end
166
+ def pop_modules(modules)
167
+ modules.each { |mod| @stack[mod].pop }
168
+ end
157
169
  end
158
170
 
159
171
  # An internal stack used to record which constants are loaded by any block.
160
- mattr_accessor :constant_watch_stack
161
- self.constant_watch_stack = WatchStack.new
172
+ mattr_accessor :constant_watch_stack, default: WatchStack.new
162
173
 
163
174
  # Module includes this module.
164
175
  module ModuleConstMissing #:nodoc:
@@ -215,6 +226,8 @@ module ActiveSupport #:nodoc:
215
226
  Dependencies.require_or_load(file_name)
216
227
  end
217
228
 
229
+ # :doc:
230
+
218
231
  # Interprets a file using <tt>mechanism</tt> and marks its defined
219
232
  # constants as autoloaded. <tt>file_name</tt> can be either a string or
220
233
  # respond to <tt>to_path</tt>.
@@ -224,7 +237,7 @@ module ActiveSupport #:nodoc:
224
237
  # resolution deterministic for constants with the same relative name in
225
238
  # different namespaces whose evaluation would depend on load order
226
239
  # otherwise.
227
- def require_dependency(file_name, message = "No such file to load -- %s")
240
+ def require_dependency(file_name, message = "No such file to load -- %s.rb")
228
241
  file_name = file_name.to_path if file_name.respond_to?(:to_path)
229
242
  unless file_name.is_a?(String)
230
243
  raise ArgumentError, "the file name must either be a String or implement #to_path -- you passed #{file_name.inspect}"
@@ -233,9 +246,13 @@ module ActiveSupport #:nodoc:
233
246
  Dependencies.depend_on(file_name, message)
234
247
  end
235
248
 
249
+ # :nodoc:
250
+
236
251
  def load_dependency(file)
237
- if Dependencies.load? && ActiveSupport::Dependencies.constant_watch_stack.watching?
238
- Dependencies.new_constants_in(Object) { yield }
252
+ if Dependencies.load? && Dependencies.constant_watch_stack.watching?
253
+ descs = Dependencies.constant_watch_stack.watching.flatten.uniq
254
+
255
+ Dependencies.new_constants_in(*descs) { yield }
239
256
  else
240
257
  yield
241
258
  end
@@ -263,17 +280,17 @@ module ActiveSupport #:nodoc:
263
280
 
264
281
  private
265
282
 
266
- def load(file, wrap = false)
267
- result = false
268
- load_dependency(file) { result = super }
269
- result
270
- end
283
+ def load(file, wrap = false)
284
+ result = false
285
+ load_dependency(file) { result = super }
286
+ result
287
+ end
271
288
 
272
- def require(file)
273
- result = false
274
- load_dependency(file) { result = super }
275
- result
276
- end
289
+ def require(file)
290
+ result = false
291
+ load_dependency(file) { result = super }
292
+ result
293
+ end
277
294
  end
278
295
 
279
296
  # Exception file-blaming.
@@ -324,56 +341,58 @@ module ActiveSupport #:nodoc:
324
341
  end
325
342
 
326
343
  def clear
327
- log_call
328
- loaded.clear
329
- loading.clear
330
- remove_unloadable_constants!
344
+ Dependencies.unload_interlock do
345
+ loaded.clear
346
+ loading.clear
347
+ remove_unloadable_constants!
348
+ end
331
349
  end
332
350
 
333
351
  def require_or_load(file_name, const_path = nil)
334
- log_call file_name, const_path
335
352
  file_name = $` if file_name =~ /\.rb\z/
336
353
  expanded = File.expand_path(file_name)
337
354
  return if loaded.include?(expanded)
338
355
 
339
- # Record that we've seen this file *before* loading it to avoid an
340
- # infinite loop with mutual dependencies.
341
- loaded << expanded
342
- loading << expanded
343
-
344
- begin
345
- if load?
346
- log "loading #{file_name}"
356
+ Dependencies.load_interlock do
357
+ # Maybe it got loaded while we were waiting for our lock:
358
+ return if loaded.include?(expanded)
347
359
 
348
- # Enable warnings if this file has not been loaded before and
349
- # warnings_on_first_load is set.
350
- load_args = ["#{file_name}.rb"]
351
- load_args << const_path unless const_path.nil?
360
+ # Record that we've seen this file *before* loading it to avoid an
361
+ # infinite loop with mutual dependencies.
362
+ loaded << expanded
363
+ loading << expanded
352
364
 
353
- if !warnings_on_first_load or history.include?(expanded)
354
- result = load_file(*load_args)
365
+ begin
366
+ if load?
367
+ # Enable warnings if this file has not been loaded before and
368
+ # warnings_on_first_load is set.
369
+ load_args = ["#{file_name}.rb"]
370
+ load_args << const_path unless const_path.nil?
371
+
372
+ if !warnings_on_first_load || history.include?(expanded)
373
+ result = load_file(*load_args)
374
+ else
375
+ enable_warnings { result = load_file(*load_args) }
376
+ end
355
377
  else
356
- enable_warnings { result = load_file(*load_args) }
378
+ result = require file_name
357
379
  end
358
- else
359
- log "requiring #{file_name}"
360
- result = require file_name
380
+ rescue Exception
381
+ loaded.delete expanded
382
+ raise
383
+ ensure
384
+ loading.pop
361
385
  end
362
- rescue Exception
363
- loaded.delete expanded
364
- raise
365
- ensure
366
- loading.pop
367
- end
368
386
 
369
- # Record history *after* loading so first load gets warnings.
370
- history << expanded
371
- result
387
+ # Record history *after* loading so first load gets warnings.
388
+ history << expanded
389
+ result
390
+ end
372
391
  end
373
392
 
374
393
  # Is the provided constant path defined?
375
394
  def qualified_const_defined?(path)
376
- Object.qualified_const_defined?(path.sub(/^::/, ''), false)
395
+ Object.const_defined?(path, false)
377
396
  end
378
397
 
379
398
  # Given +path+, a filesystem path to a ruby file, return an array of
@@ -386,13 +405,13 @@ module ActiveSupport #:nodoc:
386
405
 
387
406
  bases.each do |root|
388
407
  expanded_root = File.expand_path(root)
389
- next unless %r{\A#{Regexp.escape(expanded_root)}(/|\\)} =~ expanded_path
408
+ next unless expanded_path.start_with?(expanded_root)
390
409
 
391
- nesting = expanded_path[(expanded_root.size)..-1]
392
- nesting = nesting[1..-1] if nesting && nesting[0] == ?/
393
- next if nesting.blank?
410
+ root_size = expanded_root.size
411
+ next if expanded_path[root_size] != ?/.freeze
394
412
 
395
- paths << nesting.camelize
413
+ nesting = expanded_path[(root_size + 1)..-1]
414
+ paths << nesting.camelize unless nesting.blank?
396
415
  end
397
416
 
398
417
  paths.uniq!
@@ -401,7 +420,7 @@ module ActiveSupport #:nodoc:
401
420
 
402
421
  # Search for a file in autoload_paths matching the provided suffix.
403
422
  def search_for_file(path_suffix)
404
- path_suffix = path_suffix.sub(/(\.rb)?$/, ".rb")
423
+ path_suffix = path_suffix.sub(/(\.rb)?$/, ".rb".freeze)
405
424
 
406
425
  autoload_paths.each do |root|
407
426
  path = File.join(root, path_suffix)
@@ -421,7 +440,7 @@ module ActiveSupport #:nodoc:
421
440
  end
422
441
 
423
442
  def load_once_path?(path)
424
- # to_s works around a ruby1.9 issue where String#starts_with?(Pathname)
443
+ # to_s works around a ruby issue where String#starts_with?(Pathname)
425
444
  # will raise a TypeError: no implicit conversion of Pathname into String
426
445
  autoload_once_paths.any? { |base| path.starts_with? base.to_s }
427
446
  end
@@ -436,6 +455,7 @@ module ActiveSupport #:nodoc:
436
455
  mod = Module.new
437
456
  into.const_set const_name, mod
438
457
  autoloaded_constants << qualified_name unless autoload_once_paths.include?(base_path)
458
+ autoloaded_constants.uniq!
439
459
  mod
440
460
  end
441
461
 
@@ -448,7 +468,6 @@ module ActiveSupport #:nodoc:
448
468
  # set of names that the file at +path+ may define. See
449
469
  # +loadable_constants_for_path+ for more details.
450
470
  def load_file(path, const_paths = loadable_constants_for_path(path))
451
- log_call path, const_paths
452
471
  const_paths = [const_paths].compact unless const_paths.is_a? Array
453
472
  parent_paths = const_paths.collect { |const_path| const_path[/.*(?=::)/] || ::Object }
454
473
 
@@ -459,7 +478,6 @@ module ActiveSupport #:nodoc:
459
478
 
460
479
  autoloaded_constants.concat newly_defined_paths unless load_once_path?(path)
461
480
  autoloaded_constants.uniq!
462
- log "loading #{path} defined #{newly_defined_paths * ', '}" unless newly_defined_paths.empty?
463
481
  result
464
482
  end
465
483
 
@@ -473,8 +491,6 @@ module ActiveSupport #:nodoc:
473
491
  # it is not possible to load the constant into from_mod, try its parent
474
492
  # module using +const_missing+.
475
493
  def load_missing_constant(from_mod, const_name)
476
- log_call from_mod, const_name
477
-
478
494
  unless qualified_const_defined?(from_mod.name) && Inflector.constantize(from_mod.name).equal?(from_mod)
479
495
  raise ArgumentError, "A copy of #{from_mod} has been removed from the module tree but is still active!"
480
496
  end
@@ -486,7 +502,7 @@ module ActiveSupport #:nodoc:
486
502
 
487
503
  if file_path
488
504
  expanded = File.expand_path(file_path)
489
- expanded.sub!(/\.rb\z/, '')
505
+ expanded.sub!(/\.rb\z/, "".freeze)
490
506
 
491
507
  if loading.include?(expanded)
492
508
  raise "Circular dependency detected while autoloading constant #{qualified_name}"
@@ -530,7 +546,7 @@ module ActiveSupport #:nodoc:
530
546
  end
531
547
 
532
548
  name_error = NameError.new("uninitialized constant #{qualified_name}", const_name)
533
- name_error.set_backtrace(caller.reject {|l| l.starts_with? __FILE__ })
549
+ name_error.set_backtrace(caller.reject { |l| l.starts_with? __FILE__ })
534
550
  raise name_error
535
551
  end
536
552
 
@@ -550,7 +566,7 @@ module ActiveSupport #:nodoc:
550
566
 
551
567
  class ClassCache
552
568
  def initialize
553
- @store = ThreadSafe::Cache.new
569
+ @store = Concurrent::Map.new
554
570
  end
555
571
 
556
572
  def empty?
@@ -574,7 +590,7 @@ module ActiveSupport #:nodoc:
574
590
 
575
591
  def store(klass)
576
592
  return self unless klass.respond_to?(:name)
577
- raise(ArgumentError, 'anonymous classes cannot be cached') if klass.name.empty?
593
+ raise(ArgumentError, "anonymous classes cannot be cached") if klass.name.empty?
578
594
  @store[klass.name] = klass
579
595
  self
580
596
  end
@@ -607,8 +623,8 @@ module ActiveSupport #:nodoc:
607
623
  def autoloaded?(desc)
608
624
  return false if desc.is_a?(Module) && desc.anonymous?
609
625
  name = to_constant_name desc
610
- return false unless qualified_const_defined? name
611
- return autoloaded_constants.include?(name)
626
+ return false unless qualified_const_defined?(name)
627
+ autoloaded_constants.include?(name)
612
628
  end
613
629
 
614
630
  # Will the provided constant descriptor be unloaded?
@@ -638,54 +654,49 @@ module ActiveSupport #:nodoc:
638
654
  # exception, any new constants are regarded as being only partially defined
639
655
  # and will be removed immediately.
640
656
  def new_constants_in(*descs)
641
- log_call(*descs)
642
-
643
657
  constant_watch_stack.watch_namespaces(descs)
644
- aborting = true
658
+ success = false
645
659
 
646
660
  begin
647
661
  yield # Now yield to the code that is to define new constants.
648
- aborting = false
662
+ success = true
649
663
  ensure
650
664
  new_constants = constant_watch_stack.new_constants
651
665
 
652
- log "New constants: #{new_constants * ', '}"
653
- return new_constants unless aborting
666
+ return new_constants if success
654
667
 
655
- log "Error during loading, removing partially loaded constants "
656
- new_constants.each { |c| remove_constant(c) }.clear
668
+ # Remove partially loaded constants.
669
+ new_constants.each { |c| remove_constant(c) }
657
670
  end
658
-
659
- []
660
671
  end
661
672
 
662
673
  # Convert the provided const desc to a qualified constant name (as a string).
663
674
  # A module, class, symbol, or string may be provided.
664
675
  def to_constant_name(desc) #:nodoc:
665
676
  case desc
666
- when String then desc.sub(/^::/, '')
667
- when Symbol then desc.to_s
668
- when Module
669
- desc.name ||
670
- raise(ArgumentError, "Anonymous modules have no name to be referenced by")
671
- else raise TypeError, "Not a valid constant descriptor: #{desc.inspect}"
677
+ when String then desc.sub(/^::/, "")
678
+ when Symbol then desc.to_s
679
+ when Module
680
+ desc.name ||
681
+ raise(ArgumentError, "Anonymous modules have no name to be referenced by")
682
+ else raise TypeError, "Not a valid constant descriptor: #{desc.inspect}"
672
683
  end
673
684
  end
674
685
 
675
686
  def remove_constant(const) #:nodoc:
676
687
  # Normalize ::Foo, ::Object::Foo, Object::Foo, Object::Object::Foo, etc. as Foo.
677
- normalized = const.to_s.sub(/\A::/, '')
678
- normalized.sub!(/\A(Object::)+/, '')
688
+ normalized = const.to_s.sub(/\A::/, "")
689
+ normalized.sub!(/\A(Object::)+/, "")
679
690
 
680
- constants = normalized.split('::')
691
+ constants = normalized.split("::")
681
692
  to_remove = constants.pop
682
693
 
683
694
  # Remove the file path from the loaded list.
684
695
  file_path = search_for_file(const.underscore)
685
696
  if file_path
686
697
  expanded = File.expand_path(file_path)
687
- expanded.sub!(/\.rb\z/, '')
688
- self.loaded.delete(expanded)
698
+ expanded.sub!(/\.rb\z/, "")
699
+ loaded.delete(expanded)
689
700
  end
690
701
 
691
702
  if constants.empty?
@@ -698,13 +709,11 @@ module ActiveSupport #:nodoc:
698
709
  # here than require the caller to be clever. We check the parent
699
710
  # rather than the very const argument because we do not want to
700
711
  # trigger Kernel#autoloads, see the comment below.
701
- parent_name = constants.join('::')
712
+ parent_name = constants.join("::")
702
713
  return unless qualified_const_defined?(parent_name)
703
714
  parent = constantize(parent_name)
704
715
  end
705
716
 
706
- log "removing constant #{const}"
707
-
708
717
  # In an autoloaded user.rb like this
709
718
  #
710
719
  # autoload :Foo, 'foo'
@@ -725,7 +734,7 @@ module ActiveSupport #:nodoc:
725
734
  begin
726
735
  constantized = parent.const_get(to_remove, false)
727
736
  rescue NameError
728
- log "the constant #{const} is not reachable anymore, skipping"
737
+ # The constant is no longer reachable, just skip it.
729
738
  return
730
739
  else
731
740
  constantized.before_remove_const if constantized.respond_to?(:before_remove_const)
@@ -735,27 +744,9 @@ module ActiveSupport #:nodoc:
735
744
  begin
736
745
  parent.instance_eval { remove_const to_remove }
737
746
  rescue NameError
738
- log "the constant #{const} is not reachable anymore, skipping"
747
+ # The constant is no longer reachable, just skip it.
739
748
  end
740
749
  end
741
-
742
- protected
743
- def log_call(*args)
744
- if log_activity?
745
- arg_str = args.collect { |arg| arg.inspect } * ', '
746
- /in `([a-z_\?\!]+)'/ =~ caller(1).first
747
- selector = $1 || '<unknown>'
748
- log "called #{selector}(#{arg_str})"
749
- end
750
- end
751
-
752
- def log(msg)
753
- logger.debug "Dependencies: #{msg}" if log_activity?
754
- end
755
-
756
- def log_activity?
757
- logger && log_activity
758
- end
759
750
  end
760
751
  end
761
752