activesupport 5.2.0 → 6.0.3.2

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 (160) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +479 -330
  3. data/MIT-LICENSE +1 -1
  4. data/README.rdoc +4 -3
  5. data/lib/active_support.rb +2 -1
  6. data/lib/active_support/actionable_error.rb +48 -0
  7. data/lib/active_support/backtrace_cleaner.rb +27 -1
  8. data/lib/active_support/cache.rb +104 -84
  9. data/lib/active_support/cache/file_store.rb +29 -30
  10. data/lib/active_support/cache/mem_cache_store.rb +14 -19
  11. data/lib/active_support/cache/memory_store.rb +15 -9
  12. data/lib/active_support/cache/null_store.rb +8 -3
  13. data/lib/active_support/cache/redis_cache_store.rb +73 -34
  14. data/lib/active_support/cache/strategy/local_cache.rb +23 -23
  15. data/lib/active_support/callbacks.rb +16 -8
  16. data/lib/active_support/concern.rb +31 -4
  17. data/lib/active_support/concurrency/load_interlock_aware_monitor.rb +18 -0
  18. data/lib/active_support/concurrency/share_lock.rb +0 -1
  19. data/lib/active_support/configurable.rb +7 -11
  20. data/lib/active_support/core_ext/array.rb +1 -1
  21. data/lib/active_support/core_ext/array/access.rb +18 -6
  22. data/lib/active_support/core_ext/array/conversions.rb +5 -5
  23. data/lib/active_support/core_ext/array/extract.rb +21 -0
  24. data/lib/active_support/core_ext/array/prepend_and_append.rb +2 -6
  25. data/lib/active_support/core_ext/class/attribute.rb +11 -16
  26. data/lib/active_support/core_ext/class/subclasses.rb +1 -1
  27. data/lib/active_support/core_ext/date/calculations.rb +6 -5
  28. data/lib/active_support/core_ext/date_and_time/calculations.rb +24 -47
  29. data/lib/active_support/core_ext/date_and_time/zones.rb +0 -1
  30. data/lib/active_support/core_ext/date_time/calculations.rb +1 -1
  31. data/lib/active_support/core_ext/date_time/conversions.rb +0 -1
  32. data/lib/active_support/core_ext/digest.rb +3 -0
  33. data/lib/active_support/core_ext/enumerable.rb +97 -68
  34. data/lib/active_support/core_ext/file/atomic.rb +1 -1
  35. data/lib/active_support/core_ext/hash.rb +1 -2
  36. data/lib/active_support/core_ext/hash/compact.rb +2 -26
  37. data/lib/active_support/core_ext/hash/conversions.rb +1 -1
  38. data/lib/active_support/core_ext/hash/deep_transform_values.rb +46 -0
  39. data/lib/active_support/core_ext/hash/except.rb +1 -1
  40. data/lib/active_support/core_ext/hash/keys.rb +0 -29
  41. data/lib/active_support/core_ext/hash/slice.rb +3 -25
  42. data/lib/active_support/core_ext/hash/transform_values.rb +2 -29
  43. data/lib/active_support/core_ext/integer/multiple.rb +1 -1
  44. data/lib/active_support/core_ext/kernel.rb +0 -1
  45. data/lib/active_support/core_ext/load_error.rb +1 -1
  46. data/lib/active_support/core_ext/module.rb +0 -1
  47. data/lib/active_support/core_ext/module/attribute_accessors.rb +7 -10
  48. data/lib/active_support/core_ext/module/attribute_accessors_per_thread.rb +13 -19
  49. data/lib/active_support/core_ext/module/delegation.rb +41 -8
  50. data/lib/active_support/core_ext/module/introspection.rb +38 -13
  51. data/lib/active_support/core_ext/module/reachable.rb +1 -6
  52. data/lib/active_support/core_ext/module/redefine_method.rb +8 -17
  53. data/lib/active_support/core_ext/numeric.rb +0 -1
  54. data/lib/active_support/core_ext/numeric/conversions.rb +124 -128
  55. data/lib/active_support/core_ext/numeric/inquiry.rb +2 -25
  56. data/lib/active_support/core_ext/object/blank.rb +1 -2
  57. data/lib/active_support/core_ext/object/duplicable.rb +7 -114
  58. data/lib/active_support/core_ext/object/json.rb +1 -0
  59. data/lib/active_support/core_ext/object/to_query.rb +5 -2
  60. data/lib/active_support/core_ext/object/try.rb +17 -7
  61. data/lib/active_support/core_ext/object/with_options.rb +1 -1
  62. data/lib/active_support/core_ext/range.rb +1 -1
  63. data/lib/active_support/core_ext/range/compare_range.rb +76 -0
  64. data/lib/active_support/core_ext/range/conversions.rb +31 -29
  65. data/lib/active_support/core_ext/range/each.rb +0 -1
  66. data/lib/active_support/core_ext/range/include_range.rb +6 -22
  67. data/lib/active_support/core_ext/range/include_time_with_zone.rb +2 -2
  68. data/lib/active_support/core_ext/regexp.rb +0 -4
  69. data/lib/active_support/core_ext/securerandom.rb +23 -3
  70. data/lib/active_support/core_ext/string/access.rb +8 -0
  71. data/lib/active_support/core_ext/string/filters.rb +42 -1
  72. data/lib/active_support/core_ext/string/inflections.rb +7 -2
  73. data/lib/active_support/core_ext/string/multibyte.rb +4 -3
  74. data/lib/active_support/core_ext/string/output_safety.rb +63 -6
  75. data/lib/active_support/core_ext/string/strip.rb +3 -1
  76. data/lib/active_support/core_ext/time/calculations.rb +31 -2
  77. data/lib/active_support/core_ext/uri.rb +2 -4
  78. data/lib/active_support/current_attributes.rb +8 -0
  79. data/lib/active_support/dependencies.rb +77 -18
  80. data/lib/active_support/dependencies/zeitwerk_integration.rb +117 -0
  81. data/lib/active_support/deprecation.rb +1 -1
  82. data/lib/active_support/deprecation/behaviors.rb +5 -1
  83. data/lib/active_support/deprecation/method_wrappers.rb +20 -13
  84. data/lib/active_support/deprecation/proxy_wrappers.rb +28 -5
  85. data/lib/active_support/deprecation/reporting.rb +1 -1
  86. data/lib/active_support/descendants_tracker.rb +55 -9
  87. data/lib/active_support/duration.rb +19 -16
  88. data/lib/active_support/duration/iso8601_parser.rb +2 -4
  89. data/lib/active_support/duration/iso8601_serializer.rb +3 -5
  90. data/lib/active_support/encrypted_configuration.rb +1 -5
  91. data/lib/active_support/encrypted_file.rb +4 -3
  92. data/lib/active_support/evented_file_update_checker.rb +39 -10
  93. data/lib/active_support/execution_wrapper.rb +1 -0
  94. data/lib/active_support/file_update_checker.rb +0 -1
  95. data/lib/active_support/gem_version.rb +4 -4
  96. data/lib/active_support/hash_with_indifferent_access.rb +36 -18
  97. data/lib/active_support/i18n.rb +1 -0
  98. data/lib/active_support/i18n_railtie.rb +18 -2
  99. data/lib/active_support/inflector/inflections.rb +1 -5
  100. data/lib/active_support/inflector/methods.rb +18 -29
  101. data/lib/active_support/inflector/transliterate.rb +47 -18
  102. data/lib/active_support/json/decoding.rb +23 -24
  103. data/lib/active_support/json/encoding.rb +6 -2
  104. data/lib/active_support/key_generator.rb +0 -32
  105. data/lib/active_support/lazy_load_hooks.rb +5 -2
  106. data/lib/active_support/locale/en.rb +33 -0
  107. data/lib/active_support/log_subscriber.rb +31 -9
  108. data/lib/active_support/logger.rb +1 -16
  109. data/lib/active_support/logger_silence.rb +28 -12
  110. data/lib/active_support/logger_thread_safe_level.rb +28 -5
  111. data/lib/active_support/message_encryptor.rb +4 -6
  112. data/lib/active_support/message_verifier.rb +5 -5
  113. data/lib/active_support/messages/metadata.rb +3 -2
  114. data/lib/active_support/messages/rotator.rb +4 -4
  115. data/lib/active_support/multibyte/chars.rb +29 -49
  116. data/lib/active_support/multibyte/unicode.rb +44 -282
  117. data/lib/active_support/notifications.rb +41 -4
  118. data/lib/active_support/notifications/fanout.rb +100 -15
  119. data/lib/active_support/notifications/instrumenter.rb +80 -9
  120. data/lib/active_support/number_helper.rb +11 -0
  121. data/lib/active_support/number_helper/number_converter.rb +4 -5
  122. data/lib/active_support/number_helper/number_to_currency_converter.rb +9 -10
  123. data/lib/active_support/number_helper/number_to_delimited_converter.rb +3 -2
  124. data/lib/active_support/number_helper/number_to_human_converter.rb +3 -2
  125. data/lib/active_support/number_helper/number_to_human_size_converter.rb +3 -2
  126. data/lib/active_support/number_helper/number_to_percentage_converter.rb +3 -1
  127. data/lib/active_support/number_helper/number_to_phone_converter.rb +2 -1
  128. data/lib/active_support/number_helper/number_to_rounded_converter.rb +5 -4
  129. data/lib/active_support/option_merger.rb +21 -3
  130. data/lib/active_support/ordered_hash.rb +1 -1
  131. data/lib/active_support/ordered_options.rb +5 -1
  132. data/lib/active_support/parameter_filter.rb +128 -0
  133. data/lib/active_support/rails.rb +0 -6
  134. data/lib/active_support/reloader.rb +4 -5
  135. data/lib/active_support/security_utils.rb +1 -1
  136. data/lib/active_support/string_inquirer.rb +0 -1
  137. data/lib/active_support/subscriber.rb +65 -22
  138. data/lib/active_support/tagged_logging.rb +13 -4
  139. data/lib/active_support/test_case.rb +92 -1
  140. data/lib/active_support/testing/assertions.rb +15 -1
  141. data/lib/active_support/testing/deprecation.rb +0 -1
  142. data/lib/active_support/testing/file_fixtures.rb +2 -0
  143. data/lib/active_support/testing/isolation.rb +2 -2
  144. data/lib/active_support/testing/method_call_assertions.rb +28 -1
  145. data/lib/active_support/testing/parallelization.rb +134 -0
  146. data/lib/active_support/testing/setup_and_teardown.rb +5 -9
  147. data/lib/active_support/testing/stream.rb +1 -2
  148. data/lib/active_support/testing/time_helpers.rb +7 -9
  149. data/lib/active_support/time_with_zone.rb +15 -5
  150. data/lib/active_support/values/time_zone.rb +14 -8
  151. data/lib/active_support/xml_mini.rb +2 -10
  152. data/lib/active_support/xml_mini/jdom.rb +2 -3
  153. data/lib/active_support/xml_mini/libxml.rb +2 -2
  154. data/lib/active_support/xml_mini/libxmlsax.rb +4 -4
  155. data/lib/active_support/xml_mini/nokogiri.rb +2 -2
  156. data/lib/active_support/xml_mini/nokogirisax.rb +3 -3
  157. data/lib/active_support/xml_mini/rexml.rb +2 -2
  158. metadata +42 -13
  159. data/lib/active_support/core_ext/kernel/agnostics.rb +0 -13
  160. data/lib/active_support/values/unicode_tables.dat +0 -0
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: d0110a46a9c1dae01d77cdc50139933d40baaed4e3d4d2aa316253350239f090
4
- data.tar.gz: ce05be98e3e753d72533c2002c42ab0ae9ce7bbcfd73b0a8a8a666c275fb4eb2
3
+ metadata.gz: ddc3765b575ed4e835c62deb6d50ce258b79785b3b8f006e0a8cd5ce029afb5c
4
+ data.tar.gz: 7cb48c556646fcb7ed94a2413309093e39f45ea6ce35f8bf2dafadcce7c4dba5
5
5
  SHA512:
6
- metadata.gz: b14730056fae2c1093e60f410cd2391fb18e590edcd7dee4e69a3c5493313154522edeb9e979fa038b3cdd897fb709c32719213e34c9fcaa3d2b8ab4f1c4a0cf
7
- data.tar.gz: 1bad53bfb9ea8ba7ef6af4a2e4af0f5e272dc712e3c0f8ac2593cb91a35653871eaa6abb6f01ac46f8a946e256241b4a0e00640e5abe4ecac1a43ff06465aceb
6
+ metadata.gz: c385b04bb40eab25a93d8d72da2ec89ac8ae4dde7cf970664615ae61c8396d2071233cbc5ef96170af91b0787f9e427298979ec9a053147210930de68ee49626
7
+ data.tar.gz: e5acd9a96d62ac48111133e99eb69d656685e7ab0596e348dcf8ff6ee9fdcc6aec073738ff40ab49a5df51e873ed4404ac2d8e4c00d12447dd2b8a1d495967e3
@@ -1,522 +1,671 @@
1
- ## Rails 5.2.0 (April 09, 2018) ##
1
+ ## Rails 6.0.3.2 (June 17, 2020) ##
2
2
 
3
- * Caching: MemCache and Redis `read_multi` and `fetch_multi` speedup.
4
- Read from the local in-memory cache before consulting the backend.
3
+ * No changes.
5
4
 
6
- *Gabriel Sobrinho*
7
5
 
8
- * Return all mappings for a timezone identifier in `country_zones`.
6
+ ## Rails 6.0.3.1 (May 18, 2020) ##
9
7
 
10
- Some timezones like `Europe/London` have multiple mappings in
11
- `ActiveSupport::TimeZone::MAPPING` so return all of them instead
12
- of the first one found by using `Hash#value`. e.g:
8
+ * [CVE-2020-8165] Deprecate Marshal.load on raw cache read in RedisCacheStore
13
9
 
14
- # Before
15
- ActiveSupport::TimeZone.country_zones("GB") # => ["Edinburgh"]
10
+ * [CVE-2020-8165] Avoid Marshal.load on raw cache value in MemCacheStore
16
11
 
17
- # After
18
- ActiveSupport::TimeZone.country_zones("GB") # => ["Edinburgh", "London"]
12
+ ## Rails 6.0.3 (May 06, 2020) ##
19
13
 
20
- Fixes #31668.
14
+ * `Array#to_sentence` no longer returns a frozen string.
21
15
 
22
- *Andrew White*
16
+ Before:
23
17
 
24
- * Add support for connection pooling on RedisCacheStore.
18
+ ['one', 'two'].to_sentence.frozen?
19
+ # => true
25
20
 
26
- *fatkodima*
21
+ After:
27
22
 
28
- * Support hash as first argument in `assert_difference`. This allows to specify multiple
29
- numeric differences in the same assertion.
23
+ ['one', 'two'].to_sentence.frozen?
24
+ # => false
30
25
 
31
- assert_difference ->{ Article.count } => 1, ->{ Post.count } => 2
26
+ *Nicolas Dular*
32
27
 
33
- *Julien Meichelbeck*
28
+ * Update `ActiveSupport::Messages::Metadata#fresh?` to work for cookies with expiry set when
29
+ `ActiveSupport.parse_json_times = true`.
34
30
 
35
- * Add missing instrumentation for `read_multi` in `ActiveSupport::Cache::Store`.
31
+ *Christian Gregg*
36
32
 
37
- *Ignatius Reza Lesmana*
38
33
 
39
- * `assert_changes` will always assert that the expression changes,
40
- regardless of `from:` and `to:` argument combinations.
34
+ ## Rails 6.0.2.2 (March 19, 2020) ##
41
35
 
42
- *Daniel Ma*
36
+ * No changes.
43
37
 
44
- * Use SHA-1 to generate non-sensitive digests, such as the ETag header.
45
38
 
46
- Enabled by default for new apps; upgrading apps can opt in by setting
47
- `config.active_support.use_sha1_digests = true`.
39
+ ## Rails 6.0.2.1 (December 18, 2019) ##
48
40
 
49
- *Dmitri Dolguikh*, *Eugene Kenny*
41
+ * No changes.
50
42
 
51
- * Changed default behaviour of `ActiveSupport::SecurityUtils.secure_compare`,
52
- to make it not leak length information even for variable length string.
53
43
 
54
- Renamed old `ActiveSupport::SecurityUtils.secure_compare` to `fixed_length_secure_compare`,
55
- and started raising `ArgumentError` in case of length mismatch of passed strings.
44
+ ## Rails 6.0.2 (December 13, 2019) ##
56
45
 
57
- *Vipul A M*
46
+ * Eager load translations during initialization.
58
47
 
59
- * Make `ActiveSupport::TimeZone.all` return only time zones that are in
60
- `ActiveSupport::TimeZone::MAPPING`.
48
+ *Diego Plentz*
61
49
 
62
- Fixes #7245.
50
+ * Use per-thread CPU time clock on `ActiveSupport::Notifications`.
63
51
 
64
- *Chris LaRose*
52
+ *George Claghorn*
65
53
 
66
- * MemCacheStore: Support expiring counters.
67
54
 
68
- Pass `expires_in: [seconds]` to `#increment` and `#decrement` options
69
- to set the Memcached TTL (time-to-live) if the counter doesn't exist.
70
- If the counter exists, Memcached doesn't extend its expiry when it's
71
- incremented or decremented.
55
+ ## Rails 6.0.1 (November 5, 2019) ##
72
56
 
73
- ```
74
- Rails.cache.increment("my_counter", 1, expires_in: 2.minutes)
75
- ```
57
+ * `ActiveSupport::SafeBuffer` supports `Enumerator` methods.
76
58
 
77
- *Takumasa Ochi*
59
+ *Shugo Maeda*
78
60
 
79
- * Handle `TZInfo::AmbiguousTime` errors.
61
+ * The Redis cache store fails gracefully when the server returns a "max number
62
+ of clients reached" error.
80
63
 
81
- Make `ActiveSupport::TimeWithZone` match Ruby's handling of ambiguous
82
- times by choosing the later period, e.g.
64
+ *Brandon Medenwald*
83
65
 
84
- Ruby:
85
- ```
86
- ENV["TZ"] = "Europe/Moscow"
87
- Time.local(2014, 10, 26, 1, 0, 0) # => 2014-10-26 01:00:00 +0300
88
- ```
66
+ * Fixed that mutating a value returned by a memory cache store would
67
+ unexpectedly change the cached value.
89
68
 
90
- Before:
91
- ```
92
- >> "2014-10-26 01:00:00".in_time_zone("Moscow")
93
- TZInfo::AmbiguousTime: 26/10/2014 01:00 is an ambiguous local time.
94
- ```
69
+ *Jonathan Hyman*
95
70
 
96
- After:
97
- ```
98
- >> "2014-10-26 01:00:00".in_time_zone("Moscow")
99
- => Sun, 26 Oct 2014 01:00:00 MSK +03:00
71
+ * The default inflectors in `zeitwerk` mode support overrides:
72
+
73
+ ```ruby
74
+ # config/initializers/zeitwerk.rb
75
+ Rails.autoloaders.each do |autoloader|
76
+ autoloader.inflector.inflect(
77
+ "html_parser" => "HTMLParser",
78
+ "ssl_error" => "SSLError"
79
+ )
80
+ end
100
81
  ```
101
82
 
102
- Fixes #17395.
83
+ That way, you can tweak how individual basenames are inflected without touching Active Support inflection rules, which are global. These inflectors fallback to `String#camelize`, so existing inflection rules are still taken into account for non-overridden basenames.
103
84
 
104
- *Andrew White*
85
+ Please, check the [autoloading guide for `zeitwerk` mode](https://guides.rubyonrails.org/v6.0/autoloading_and_reloading_constants.html#customizing-inflections) if you prefer not to depend on `String#camelize` at all.
105
86
 
106
- * Redis cache store.
87
+ *Xavier Noria*
107
88
 
108
- ```
109
- # Defaults to `redis://localhost:6379/0`. Only use for dev/test.
110
- config.cache_store = :redis_cache_store
111
-
112
- # Supports all common cache store options (:namespace, :compress,
113
- # :compress_threshold, :expires_in, :race_condition_ttl) and all
114
- # Redis options.
115
- cache_password = Rails.application.secrets.redis_cache_password
116
- config.cache_store = :redis_cache_store, driver: :hiredis,
117
- namespace: 'myapp-cache', compress: true, timeout: 1,
118
- url: "redis://:#{cache_password}@myapp-cache-1:6379/0"
119
-
120
- # Supports Redis::Distributed with multiple hosts
121
- config.cache_store = :redis_cache_store, driver: :hiredis
122
- namespace: 'myapp-cache', compress: true,
123
- url: %w[
124
- redis://myapp-cache-1:6379/0
125
- redis://myapp-cache-1:6380/0
126
- redis://myapp-cache-2:6379/0
127
- redis://myapp-cache-2:6380/0
128
- redis://myapp-cache-3:6379/0
129
- redis://myapp-cache-3:6380/0
130
- ]
131
-
132
- # Or pass a builder block
133
- config.cache_store = :redis_cache_store,
134
- namespace: 'myapp-cache', compress: true,
135
- redis: -> { Redis.new … }
136
- ```
89
+ * Improve `Range#===`, `Range#include?`, and `Range#cover?` to work with beginless (startless)
90
+ and endless range targets.
137
91
 
138
- Deployment note: Take care to use a *dedicated Redis cache* rather
139
- than pointing this at your existing Redis server. It won't cope well
140
- with mixed usage patterns and it won't expire cache entries by default.
92
+ *Allen Hsu*, *Andrew Hodgkinson*
141
93
 
142
- Redis cache server setup guide: https://redis.io/topics/lru-cache
94
+ * Don't use `Process#clock_gettime(CLOCK_THREAD_CPUTIME_ID)` on Solaris.
143
95
 
144
- *Jeremy Daer*
96
+ *Iain Beeston*
145
97
 
146
- * Cache: Enable compression by default for values > 1kB.
147
98
 
148
- Compression has long been available, but opt-in and at a 16kB threshold.
149
- It wasn't enabled by default due to CPU cost. Today it's cheap and typical
150
- cache data is eminently compressible, such as HTML or JSON fragments.
151
- Compression dramatically reduces Memcached/Redis mem usage, which means
152
- the same cache servers can store more data, which means higher hit rates.
99
+ ## Rails 6.0.0 (August 16, 2019) ##
153
100
 
154
- To disable compression, pass `compress: false` to the initializer.
101
+ * Let `require_dependency` in `zeitwerk` mode look the autoload paths up for
102
+ better backwards compatibility.
155
103
 
156
- *Jeremy Daer*
104
+ *Xavier Noria*
157
105
 
158
- * Allow `Range#include?` on TWZ ranges.
106
+ * Let `require_dependency` in `zeitwerk` mode support arguments that respond
107
+ to `to_path` for better backwards compatibility.
159
108
 
160
- In #11474 we prevented TWZ ranges being iterated over which matched
161
- Ruby's handling of Time ranges and as a consequence `include?`
162
- stopped working with both Time ranges and TWZ ranges. However in
163
- ruby/ruby@b061634 support was added for `include?` to use `cover?`
164
- for 'linear' objects. Since we have no way of making Ruby consider
165
- TWZ instances as 'linear' we have to override `Range#include?`.
109
+ *Xavier Noria*
166
110
 
167
- Fixes #30799.
111
+ * Make ActiveSupport::Logger Fiber-safe. Fixes #36752.
168
112
 
169
- *Andrew White*
113
+ Use `Fiber.current.__id__` in `ActiveSupport::Logger#local_level=` in order
114
+ to make log level local to Ruby Fibers in addition to Threads.
170
115
 
171
- * Fix acronym support in `humanize`.
116
+ Example:
172
117
 
173
- Acronym inflections are stored with lowercase keys in the hash but
174
- the match wasn't being lowercased before being looked up in the hash.
175
- This shouldn't have any performance impact because before it would
176
- fail to find the acronym and perform the `downcase` operation anyway.
118
+ logger = ActiveSupport::Logger.new(STDOUT)
119
+ logger.level = 1
120
+ p "Main is debug? #{logger.debug?}"
177
121
 
178
- Fixes #31052.
122
+ Fiber.new {
123
+ logger.local_level = 0
124
+ p "Thread is debug? #{logger.debug?}"
125
+ }.resume
179
126
 
180
- *Andrew White*
127
+ p "Main is debug? #{logger.debug?}"
128
+
129
+ Before:
130
+
131
+ Main is debug? false
132
+ Thread is debug? true
133
+ Main is debug? true
134
+
135
+ After:
136
+
137
+ Main is debug? false
138
+ Thread is debug? true
139
+ Main is debug? false
140
+
141
+ *Alexander Varnin*
181
142
 
182
- * Add same method signature for `Time#prev_year` and `Time#next_year`
183
- in accordance with `Date#prev_year`, `Date#next_year`.
143
+ * Do not delegate missing `marshal_dump` and `_dump` methods via the
144
+ `delegate_missing_to` extension. This avoids unintentionally adding instance
145
+ variables when calling `Marshal.dump(object)`, should the delegation target of
146
+ `object` be a method which would otherwise add them. Fixes #36522.
184
147
 
185
- Allows pass argument for `Time#prev_year` and `Time#next_year`.
148
+ *Aaron Lipman*
149
+
150
+
151
+ ## Rails 6.0.0.rc2 (July 22, 2019) ##
152
+
153
+ * `truncate` would return the original string if it was too short to be truncated
154
+ and a frozen string if it were long enough to be truncated. Now truncate will
155
+ consistently return an unfrozen string regardless. This behavior is consistent
156
+ with `gsub` and `strip`.
186
157
 
187
158
  Before:
188
- ```
189
- Time.new(2017, 9, 16, 17, 0).prev_year # => 2016-09-16 17:00:00 +0300
190
- Time.new(2017, 9, 16, 17, 0).prev_year(1)
191
- # => ArgumentError: wrong number of arguments (given 1, expected 0)
192
159
 
193
- Time.new(2017, 9, 16, 17, 0).next_year # => 2018-09-16 17:00:00 +0300
194
- Time.new(2017, 9, 16, 17, 0).next_year(1)
195
- # => ArgumentError: wrong number of arguments (given 1, expected 0)
196
- ```
160
+ 'foobar'.truncate(5).frozen?
161
+ # => true
162
+ 'foobar'.truncate(6).frozen?
163
+ # => false
197
164
 
198
165
  After:
199
- ```
200
- Time.new(2017, 9, 16, 17, 0).prev_year # => 2016-09-16 17:00:00 +0300
201
- Time.new(2017, 9, 16, 17, 0).prev_year(1) # => 2016-09-16 17:00:00 +0300
202
166
 
203
- Time.new(2017, 9, 16, 17, 0).next_year # => 2018-09-16 17:00:00 +0300
204
- Time.new(2017, 9, 16, 17, 0).next_year(1) # => 2018-09-16 17:00:00 +0300
167
+ 'foobar'.truncate(5).frozen?
168
+ # => false
169
+ 'foobar'.truncate(6).frozen?
170
+ # => false
171
+
172
+ *Jordan Thomas*
173
+
174
+
175
+ ## Rails 6.0.0.rc1 (April 24, 2019) ##
176
+
177
+ * Introduce `ActiveSupport::ActionableError`.
178
+
179
+ Actionable errors let's you dispatch actions from Rails' error pages. This
180
+ can help you save time if you have a clear action for the resolution of
181
+ common development errors.
182
+
183
+ The de-facto example are pending migrations. Every time pending migrations
184
+ are found, a middleware raises an error. With actionable errors, you can
185
+ run the migrations right from the error page. Other examples include Rails
186
+ plugins that need to run a rake task to setup themselves. They can now
187
+ raise actionable errors to run the setup straight from the error pages.
188
+
189
+ Here is how to define an actionable error:
190
+
191
+ ```ruby
192
+ class PendingMigrationError < MigrationError #:nodoc:
193
+ include ActiveSupport::ActionableError
194
+
195
+ action "Run pending migrations" do
196
+ ActiveRecord::Tasks::DatabaseTasks.migrate
197
+ end
198
+ end
205
199
  ```
206
200
 
207
- *bogdanvlviv*
201
+ To make an error actionable, include the `ActiveSupport::ActionableError`
202
+ module and invoke the `action` class macro to define the action. An action
203
+ needs a name and a procedure to execute. The name is shown as the name of a
204
+ button on the error pages. Once clicked, it will invoke the given
205
+ procedure.
208
206
 
209
- * Add same method signature for `Time#prev_month` and `Time#next_month`
210
- in accordance with `Date#prev_month`, `Date#next_month`.
207
+ *Vipul A M*, *Yao Jie*, *Genadi Samokovarov*
211
208
 
212
- Allows pass argument for `Time#prev_month` and `Time#next_month`.
209
+ * Preserve `html_safe?` status on `ActiveSupport::SafeBuffer#*`.
213
210
 
214
211
  Before:
215
- ```
216
- Time.new(2017, 9, 16, 17, 0).prev_month # => 2017-08-16 17:00:00 +0300
217
- Time.new(2017, 9, 16, 17, 0).prev_month(1)
218
- # => ArgumentError: wrong number of arguments (given 1, expected 0)
219
212
 
220
- Time.new(2017, 9, 16, 17, 0).next_month # => 2017-10-16 17:00:00 +0300
221
- Time.new(2017, 9, 16, 17, 0).next_month(1)
222
- # => ArgumentError: wrong number of arguments (given 1, expected 0)
223
- ```
213
+ ("<br />".html_safe * 2).html_safe? #=> nil
224
214
 
225
215
  After:
226
- ```
227
- Time.new(2017, 9, 16, 17, 0).prev_month # => 2017-08-16 17:00:00 +0300
228
- Time.new(2017, 9, 16, 17, 0).prev_month(1) # => 2017-08-16 17:00:00 +0300
229
216
 
230
- Time.new(2017, 9, 16, 17, 0).next_month # => 2017-10-16 17:00:00 +0300
231
- Time.new(2017, 9, 16, 17, 0).next_month(1) # => 2017-10-16 17:00:00 +0300
232
- ```
217
+ ("<br />".html_safe * 2).html_safe? #=> true
233
218
 
234
- *bogdanvlviv*
219
+ *Ryo Nakamura*
220
+
221
+ * Calling test methods with `with_info_handler` method to allow minitest-hooks
222
+ plugin to work.
223
+
224
+ *Mauri Mustonen*
225
+
226
+ * The Zeitwerk compatibility interface for `ActiveSupport::Dependencies` no
227
+ longer implements `autoloaded_constants` or `autoloaded?` (undocumented,
228
+ anyway). Experience shows introspection does not have many use cases, and
229
+ troubleshooting is done by logging. With this design trade-off we are able
230
+ to use even less memory in all environments.
231
+
232
+ *Xavier Noria*
233
+
234
+ * Depends on Zeitwerk 2, which stores less metadata if reloading is disabled
235
+ and hence uses less memory when `config.cache_classes` is `true`, a standard
236
+ setup in production.
237
+
238
+ *Xavier Noria*
235
239
 
236
- * Add same method signature for `Time#prev_day` and `Time#next_day`
237
- in accordance with `Date#prev_day`, `Date#next_day`.
240
+ * In `:zeitwerk` mode, eager load directories in engines and applications only
241
+ if present in their respective `config.eager_load_paths`.
238
242
 
239
- Allows pass argument for `Time#prev_day` and `Time#next_day`.
243
+ A common use case for this is adding `lib` to `config.autoload_paths`, but
244
+ not to `config.eager_load_paths`. In that configuration, for example, files
245
+ in the `lib` directory should not be eager loaded.
246
+
247
+ *Xavier Noria*
248
+
249
+ * Fix bug in Range comparisons when comparing to an excluded-end Range
240
250
 
241
251
  Before:
242
- ```
243
- Time.new(2017, 9, 16, 17, 0).prev_day # => 2017-09-15 17:00:00 +0300
244
- Time.new(2017, 9, 16, 17, 0).prev_day(1)
245
- # => ArgumentError: wrong number of arguments (given 1, expected 0)
246
252
 
247
- Time.new(2017, 9, 16, 17, 0).next_day # => 2017-09-17 17:00:00 +0300
248
- Time.new(2017, 9, 16, 17, 0).next_day(1)
249
- # => ArgumentError: wrong number of arguments (given 1, expected 0)
250
- ```
253
+ (1..10).cover?(1...11) # => false
251
254
 
252
255
  After:
253
- ```
254
- Time.new(2017, 9, 16, 17, 0).prev_day # => 2017-09-15 17:00:00 +0300
255
- Time.new(2017, 9, 16, 17, 0).prev_day(1) # => 2017-09-15 17:00:00 +0300
256
256
 
257
- Time.new(2017, 9, 16, 17, 0).next_day # => 2017-09-17 17:00:00 +0300
258
- Time.new(2017, 9, 16, 17, 0).next_day(1) # => 2017-09-17 17:00:00 +0300
259
- ```
257
+ (1..10).cover?(1...11) # => true
260
258
 
261
- *bogdanvlviv*
259
+ With the same change for `Range#include?` and `Range#===`.
260
+
261
+ *Owen Stephens*
262
+
263
+ * Use weak references in descendants tracker to allow anonymous subclasses to
264
+ be garbage collected.
262
265
 
263
- * `IO#to_json` now returns the `to_s` representation, rather than
264
- attempting to convert to an array. This fixes a bug where `IO#to_json`
265
- would raise an `IOError` when called on an unreadable object.
266
+ *Edgars Beigarts*
266
267
 
267
- Fixes #26132.
268
+ * Update `ActiveSupport::Notifications::Instrumenter#instrument` to make
269
+ passing a block optional. This will let users use
270
+ `ActiveSupport::Notifications` messaging features outside of
271
+ instrumentation.
268
272
 
269
- *Paul Kuruvilla*
273
+ *Ali Ibrahim*
270
274
 
271
- * Remove deprecated `halt_callback_chains_on_return_false` option.
275
+ * Fix `Time#advance` to work with dates before 1001-03-07
276
+
277
+ Before:
278
+
279
+ Time.utc(1001, 3, 6).advance(years: -1) # => 1000-03-05 00:00:00 UTC
280
+
281
+ After
282
+
283
+ Time.utc(1001, 3, 6).advance(years: -1) # => 1000-03-06 00:00:00 UTC
284
+
285
+ Note that this doesn't affect `DateTime#advance` as that doesn't use a proleptic calendar.
286
+
287
+ *Andrew White*
288
+
289
+ * In Zeitwerk mode, engines are now managed by the `main` autoloader. Engines may reference application constants, if the application is reloaded and we do not reload engines, they won't use the reloaded application code.
290
+
291
+ *Xavier Noria*
292
+
293
+ * Add support for supplying `locale` to `transliterate` and `parameterize`.
294
+
295
+ I18n.backend.store_translations(:de, i18n: { transliterate: { rule: { "ü" => "ue" } } })
296
+
297
+ ActiveSupport::Inflector.transliterate("ü", locale: :de) # => "ue"
298
+ "Fünf autos".parameterize(locale: :de) # => "fuenf-autos"
299
+ ActiveSupport::Inflector.parameterize("Fünf autos", locale: :de) # => "fuenf-autos"
300
+
301
+ *Kaan Ozkan*, *Sharang Dashputre*
302
+
303
+ * Allow `Array#excluding` and `Enumerable#excluding` to deal with a passed array gracefully.
304
+
305
+ [ 1, 2, 3, 4, 5 ].excluding([4, 5]) # => [ 1, 2, 3 ]
306
+
307
+ *DHH*
308
+
309
+ * Renamed `Array#without` and `Enumerable#without` to `Array#excluding` and `Enumerable#excluding`, to create parity with
310
+ `Array#including` and `Enumerable#including`. Retained the old names as aliases.
311
+
312
+ *DHH*
313
+
314
+ * Added `Array#including` and `Enumerable#including` to conveniently enlarge a collection with more members using a method rather than an operator:
315
+
316
+ [ 1, 2, 3 ].including(4, 5) # => [ 1, 2, 3, 4, 5 ]
317
+ post.authors.including(Current.person) # => All the authors plus the current person!
318
+
319
+ *DHH*
320
+
321
+
322
+ ## Rails 6.0.0.beta3 (March 11, 2019) ##
323
+
324
+ * No changes.
325
+
326
+
327
+ ## Rails 6.0.0.beta2 (February 25, 2019) ##
328
+
329
+ * New autoloading based on [Zeitwerk](https://github.com/fxn/zeitwerk).
330
+
331
+ *Xavier Noria*
332
+
333
+ * Revise `ActiveSupport::Notifications.unsubscribe` to correctly handle Regex or other multiple-pattern subscribers.
334
+
335
+ *Zach Kemp*
336
+
337
+ * Add `before_reset` callback to `CurrentAttributes` and define `after_reset` as an alias of `resets` for symmetry.
338
+
339
+ *Rosa Gutierrez*
340
+
341
+ * Remove the `` Kernel#` `` override that suppresses ENOENT and accidentally returns nil on Unix systems.
342
+
343
+ *Akinori Musha*
344
+
345
+ * Add `ActiveSupport::HashWithIndifferentAccess#assoc`.
346
+
347
+ `assoc` can now be called with either a string or a symbol.
348
+
349
+ *Stefan Schüßler*
350
+
351
+ * Add `Hash#deep_transform_values`, and `Hash#deep_transform_values!`.
352
+
353
+ *Guillermo Iguaran*
354
+
355
+
356
+ ## Rails 6.0.0.beta1 (January 18, 2019) ##
357
+
358
+ * Remove deprecated `Module#reachable?` method.
272
359
 
273
360
  *Rafael Mendonça França*
274
361
 
275
- * Remove deprecated `:if` and `:unless` string filter for callbacks.
362
+ * Remove deprecated `#acronym_regex` method from `Inflections`.
276
363
 
277
364
  *Rafael Mendonça França*
278
365
 
279
- * `Hash#slice` now falls back to Ruby 2.5+'s built-in definition if defined.
366
+ * Fix `String#safe_constantize` throwing a `LoadError` for incorrectly cased constant references.
280
367
 
281
- *Akira Matsuda*
368
+ *Keenan Brock*
282
369
 
283
- * Deprecate `secrets.secret_token`.
370
+ * Preserve key order passed to `ActiveSupport::CacheStore#fetch_multi`.
284
371
 
285
- The architecture for secrets had a big upgrade between Rails 3 and Rails 4,
286
- when the default changed from using `secret_token` to `secret_key_base`.
372
+ `fetch_multi(*names)` now returns its results in the same order as the `*names` requested, rather than returning cache hits followed by cache misses.
287
373
 
288
- `secret_token` has been soft deprecated in documentation for four years
289
- but is still in place to support apps created before Rails 4.
290
- Deprecation warnings have been added to help developers upgrade their
291
- applications to `secret_key_base`.
374
+ *Gannon McGibbon*
292
375
 
293
- *claudiob*, *Kasper Timm Hansen*
376
+ * If the same block is `included` multiple times for a Concern, an exception is no longer raised.
294
377
 
295
- * Return an instance of `HashWithIndifferentAccess` from `HashWithIndifferentAccess#transform_keys`.
378
+ *Mark J. Titorenko*, *Vlad Bokov*
296
379
 
297
- *Yuji Yaginuma*
380
+ * Fix bug where `#to_options` for `ActiveSupport::HashWithIndifferentAccess`
381
+ would not act as alias for `#symbolize_keys`.
298
382
 
299
- * Add key rotation support to `MessageEncryptor` and `MessageVerifier`.
383
+ *Nick Weiland*
300
384
 
301
- This change introduces a `rotate` method to both the `MessageEncryptor` and
302
- `MessageVerifier` classes. This method accepts the same arguments and
303
- options as the given classes' constructor. The `encrypt_and_verify` method
304
- for `MessageEncryptor` and the `verified` method for `MessageVerifier` also
305
- accept an optional keyword argument `:on_rotation` block which is called
306
- when a rotated instance is used to decrypt or verify the message.
385
+ * Improve the logic that detects non-autoloaded constants.
307
386
 
308
- *Michael J Coyne*
387
+ *Jan Habermann*, *Xavier Noria*
309
388
 
310
- * Deprecate `Module#reachable?` method.
389
+ * Deprecate `ActiveSupport::Multibyte::Unicode#pack_graphemes(array)` and `ActiveSupport::Multibyte::Unicode#unpack_graphemes(string)`
390
+ in favor of `array.flatten.pack("U*")` and `string.scan(/\X/).map(&:codepoints)`, respectively.
311
391
 
312
- *bogdanvlviv*
392
+ *Francesco Rodríguez*
313
393
 
314
- * Add `config/credentials.yml.enc` to store production app secrets.
394
+ * Deprecate `ActiveSupport::Multibyte::Chars.consumes?` in favor of `String#is_utf8?`.
315
395
 
316
- Allows saving any authentication credentials for third party services
317
- directly in repo encrypted with `config/master.key` or `ENV["RAILS_MASTER_KEY"]`.
396
+ *Francesco Rodríguez*
318
397
 
319
- This will eventually replace `Rails.application.secrets` and the encrypted
320
- secrets introduced in Rails 5.1.
398
+ * Fix duration being rounded to a full second.
399
+ ```
400
+ time = DateTime.parse("2018-1-1")
401
+ time += 0.51.seconds
402
+ ```
403
+ Will now correctly add 0.51 second and not 1 full second.
321
404
 
322
- *DHH*, *Kasper Timm Hansen*
405
+ *Edouard Chin*
323
406
 
324
- * Add `ActiveSupport::EncryptedFile` and `ActiveSupport::EncryptedConfiguration`.
407
+ * Deprecate `ActiveSupport::Multibyte::Unicode#normalize` and `ActiveSupport::Multibyte::Chars#normalize`
408
+ in favor of `String#unicode_normalize`
325
409
 
326
- Allows for stashing encrypted files or configuration directly in repo by
327
- encrypting it with a key.
410
+ *Francesco Rodríguez*
328
411
 
329
- Backs the new credentials setup above, but can also be used independently.
412
+ * Deprecate `ActiveSupport::Multibyte::Unicode#downcase/upcase/swapcase` in favor of
413
+ `String#downcase/upcase/swapcase`.
330
414
 
331
- *DHH*, *Kasper Timm Hansen*
415
+ *Francesco Rodríguez*
332
416
 
333
- * `Module#delegate_missing_to` now raises `DelegationError` if target is nil,
334
- similar to `Module#delegate`.
417
+ * Add `ActiveSupport::ParameterFilter`.
335
418
 
336
- *Anton Khamets*
419
+ *Yoshiyuki Kinjo*
337
420
 
338
- * Update `String#camelize` to provide feedback when wrong option is passed.
421
+ * Rename `Module#parent`, `Module#parents`, and `Module#parent_name` to
422
+ `module_parent`, `module_parents`, and `module_parent_name`.
339
423
 
340
- `String#camelize` was returning nil without any feedback when an
341
- invalid option was passed as a parameter.
424
+ *Gannon McGibbon*
342
425
 
343
- Previously:
426
+ * Deprecate the use of `LoggerSilence` in favor of `ActiveSupport::LoggerSilence`
344
427
 
345
- 'one_two'.camelize(true)
346
- # => nil
428
+ *Edouard Chin*
347
429
 
348
- Now:
430
+ * Deprecate using negative limits in `String#first` and `String#last`.
349
431
 
350
- 'one_two'.camelize(true)
351
- # => ArgumentError: Invalid option, use either :upper or :lower.
432
+ *Gannon McGibbon*, *Eric Turner*
352
433
 
353
- *Ricardo Díaz*
434
+ * Fix bug where `#without` for `ActiveSupport::HashWithIndifferentAccess` would fail
435
+ with symbol arguments
354
436
 
355
- * Fix modulo operations involving durations.
437
+ *Abraham Chan*
356
438
 
357
- Rails 5.1 introduced `ActiveSupport::Duration::Scalar` as a wrapper
358
- around numeric values as a way of ensuring a duration was the outcome of
359
- an expression. However, the implementation was missing support for modulo
360
- operations. This support has now been added and should result in a duration
361
- being returned from expressions involving modulo operations.
439
+ * Treat `#delete_prefix`, `#delete_suffix` and `#unicode_normalize` results as non-`html_safe`.
440
+ Ensure safety of arguments for `#insert`, `#[]=` and `#replace` calls on `html_safe` Strings.
362
441
 
363
- Prior to Rails 5.1:
442
+ *Janosch Müller*
364
443
 
365
- 5.minutes % 2.minutes
366
- # => 60
444
+ * Changed `ActiveSupport::TaggedLogging.new` to return a new logger instance instead
445
+ of mutating the one received as parameter.
367
446
 
368
- Now:
447
+ *Thierry Joyal*
369
448
 
370
- 5.minutes % 2.minutes
371
- # => 1 minute
449
+ * Define `unfreeze_time` as an alias of `travel_back` in `ActiveSupport::Testing::TimeHelpers`.
372
450
 
373
- Fixes #29603 and #29743.
451
+ The alias is provided for symmetry with `freeze_time`.
374
452
 
375
- *Sayan Chakraborty*, *Andrew White*
453
+ *Ryan Davidson*
376
454
 
377
- * Fix division where a duration is the denominator.
455
+ * Add support for tracing constant autoloads. Just throw
378
456
 
379
- PR #29163 introduced a change in behavior when a duration was the denominator
380
- in a calculation - this was incorrect as dividing by a duration should always
381
- return a `Numeric`. The behavior of previous versions of Rails has been restored.
457
+ ActiveSupport::Dependencies.logger = Rails.logger
458
+ ActiveSupport::Dependencies.verbose = true
382
459
 
383
- Fixes #29592.
460
+ in an initializer.
384
461
 
385
- *Andrew White*
462
+ *Xavier Noria*
386
463
 
387
- * Add purpose and expiry support to `ActiveSupport::MessageVerifier` and
388
- `ActiveSupport::MessageEncryptor`.
464
+ * Maintain `html_safe?` on html_safe strings when sliced.
389
465
 
390
- For instance, to ensure a message is only usable for one intended purpose:
466
+ string = "<div>test</div>".html_safe
467
+ string[-1..1].html_safe? # => true
391
468
 
392
- token = @verifier.generate("x", purpose: :shipping)
469
+ *Elom Gomez*, *Yumin Wong*
393
470
 
394
- @verifier.verified(token, purpose: :shipping) # => "x"
395
- @verifier.verified(token) # => nil
471
+ * Add `Array#extract!`.
396
472
 
397
- Or make it expire after a set time:
473
+ The method removes and returns the elements for which the block returns a true value.
474
+ If no block is given, an Enumerator is returned instead.
398
475
 
399
- @verifier.generate("x", expires_in: 1.month)
400
- @verifier.generate("y", expires_at: Time.now.end_of_year)
476
+ numbers = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
477
+ odd_numbers = numbers.extract! { |number| number.odd? } # => [1, 3, 5, 7, 9]
478
+ numbers # => [0, 2, 4, 6, 8]
401
479
 
402
- Showcased with `ActiveSupport::MessageVerifier`, but works the same for
403
- `ActiveSupport::MessageEncryptor`'s `encrypt_and_sign` and `decrypt_and_verify`.
480
+ *bogdanvlviv*
404
481
 
405
- Pull requests: #29599, #29854
482
+ * Support not to cache `nil` for `ActiveSupport::Cache#fetch`.
406
483
 
407
- *Assain Jaleel*
484
+ cache.fetch('bar', skip_nil: true) { nil }
485
+ cache.exist?('bar') # => false
408
486
 
409
- * Make the order of `Hash#reverse_merge!` consistent with `HashWithIndifferentAccess`.
487
+ *Martin Hong*
410
488
 
411
- *Erol Fornoles*
489
+ * Add "event object" support to the notification system.
490
+ Before this change, end users were forced to create hand made artisanal
491
+ event objects on their own, like this:
412
492
 
413
- * Add `freeze_time` helper which freezes time to `Time.now` in tests.
493
+ ActiveSupport::Notifications.subscribe('wait') do |*args|
494
+ @event = ActiveSupport::Notifications::Event.new(*args)
495
+ end
414
496
 
415
- *Prathamesh Sonpatki*
497
+ ActiveSupport::Notifications.instrument('wait') do
498
+ sleep 1
499
+ end
416
500
 
417
- * Default `ActiveSupport::MessageEncryptor` to use AES 256 GCM encryption.
501
+ @event.duration # => 1000.138
418
502
 
419
- On for new Rails 5.2 apps. Upgrading apps can find the config as a new
420
- framework default.
503
+ After this change, if the block passed to `subscribe` only takes one
504
+ parameter, the framework will yield an event object to the block. Now
505
+ end users are no longer required to make their own:
421
506
 
422
- *Assain Jaleel*
507
+ ActiveSupport::Notifications.subscribe('wait') do |event|
508
+ @event = event
509
+ end
423
510
 
424
- * Cache: `write_multi`.
511
+ ActiveSupport::Notifications.instrument('wait') do
512
+ sleep 1
513
+ end
425
514
 
426
- Rails.cache.write_multi foo: 'bar', baz: 'qux'
515
+ p @event.allocations # => 7
516
+ p @event.cpu_time # => 0.256
517
+ p @event.idle_time # => 1003.2399
427
518
 
428
- Plus faster fetch_multi with stores that implement `write_multi_entries`.
429
- Keys that aren't found may be written to the cache store in one shot
430
- instead of separate writes.
519
+ Now you can enjoy event objects without making them yourself. Neat!
431
520
 
432
- The default implementation simply calls `write_entry` for each entry.
433
- Stores may override if they're capable of one-shot bulk writes, like
434
- Redis `MSET`.
521
+ *Aaron "t.lo" Patterson*
435
522
 
436
- *Jeremy Daer*
523
+ * Add cpu_time, idle_time, and allocations to Event.
437
524
 
438
- * Add default option to module and class attribute accessors.
525
+ *Eileen M. Uchitelle*, *Aaron Patterson*
439
526
 
440
- mattr_accessor :settings, default: {}
527
+ * RedisCacheStore: support key expiry in increment/decrement.
441
528
 
442
- Works for `mattr_reader`, `mattr_writer`, `cattr_accessor`, `cattr_reader`,
443
- and `cattr_writer` as well.
529
+ Pass `:expires_in` to `#increment` and `#decrement` to set a Redis EXPIRE on the key.
444
530
 
445
- *Genadi Samokovarov*
531
+ If the key is already set to expire, RedisCacheStore won't extend its expiry.
446
532
 
447
- * Add `Date#prev_occurring` and `Date#next_occurring` to return specified next/previous occurring day of week.
533
+ Rails.cache.increment("some_key", 1, expires_in: 2.minutes)
448
534
 
449
- *Shota Iguchi*
535
+ *Jason Lee*
450
536
 
451
- * Add default option to `class_attribute`.
537
+ * Allow `Range#===` and `Range#cover?` on Range.
452
538
 
453
- Before:
539
+ `Range#cover?` can now accept a range argument like `Range#include?` and
540
+ `Range#===`. `Range#===` works correctly on Ruby 2.6. `Range#include?` is moved
541
+ into a new file, with these two methods.
454
542
 
455
- class_attribute :settings
456
- self.settings = {}
543
+ *Requiring active_support/core_ext/range/include_range is now deprecated.*
544
+ *Use `require "active_support/core_ext/range/compare_range"` instead.*
457
545
 
458
- Now:
546
+ *utilum*
459
547
 
460
- class_attribute :settings, default: {}
548
+ * Add `index_with` to Enumerable.
461
549
 
462
- *DHH*
550
+ Allows creating a hash from an enumerable with the value from a passed block
551
+ or a default argument.
463
552
 
464
- * `#singularize` and `#pluralize` now respect uncountables for the specified locale.
553
+ %i( title body ).index_with { |attr| post.public_send(attr) }
554
+ # => { title: "hey", body: "what's up?" }
465
555
 
466
- *Eilis Hamilton*
556
+ %i( title body ).index_with(nil)
557
+ # => { title: nil, body: nil }
467
558
 
468
- * Add `ActiveSupport::CurrentAttributes` to provide a thread-isolated attributes singleton.
469
- Primary use case is keeping all the per-request attributes easily available to the whole system.
559
+ Closely linked with `index_by`, which creates a hash where the keys are extracted from a block.
470
560
 
471
- *DHH*
561
+ *Kasper Timm Hansen*
472
562
 
473
- * Fix implicit coercion calculations with scalars and durations.
563
+ * Fix bug where `ActiveSupport::TimeZone.all` would fail when tzinfo data for
564
+ any timezone defined in `ActiveSupport::TimeZone::MAPPING` is missing.
474
565
 
475
- Previously, calculations where the scalar is first would be converted to a duration
476
- of seconds, but this causes issues with dates being converted to times, e.g:
566
+ *Dominik Sander*
477
567
 
478
- Time.zone = "Beijing" # => Asia/Shanghai
479
- date = Date.civil(2017, 5, 20) # => Mon, 20 May 2017
480
- 2 * 1.day # => 172800 seconds
481
- date + 2 * 1.day # => Mon, 22 May 2017 00:00:00 CST +08:00
568
+ * Redis cache store: `delete_matched` no longer blocks the Redis server.
569
+ (Switches from evaled Lua to a batched SCAN + DEL loop.)
482
570
 
483
- Now, the `ActiveSupport::Duration::Scalar` calculation methods will try to maintain
484
- the part structure of the duration where possible, e.g:
571
+ *Gleb Mazovetskiy*
485
572
 
486
- Time.zone = "Beijing" # => Asia/Shanghai
487
- date = Date.civil(2017, 5, 20) # => Mon, 20 May 2017
488
- 2 * 1.day # => 2 days
489
- date + 2 * 1.day # => Mon, 22 May 2017
573
+ * Fix bug where `ActiveSupport::Cache` will massively inflate the storage
574
+ size when compression is enabled (which is true by default). This patch
575
+ does not attempt to repair existing data: please manually flush the cache
576
+ to clear out the problematic entries.
490
577
 
491
- Fixes #29160, #28970.
578
+ *Godfrey Chan*
492
579
 
493
- *Andrew White*
580
+ * Fix bug where `URI.unescape` would fail with mixed Unicode/escaped character input:
494
581
 
495
- * Add support for versioned cache entries. This enables the cache stores to recycle cache keys, greatly saving
496
- on storage in cases with frequent churn. Works together with the separation of `#cache_key` and `#cache_version`
497
- in Active Record and its use in Action Pack's fragment caching.
582
+ URI.unescape("\xe3\x83\x90") # => "バ"
583
+ URI.unescape("%E3%83%90") # => "バ"
584
+ URI.unescape("\xe3\x83\x90%E3%83%90") # => Encoding::CompatibilityError
498
585
 
499
- *DHH*
586
+ *Ashe Connor*, *Aaron Patterson*
500
587
 
501
- * Pass gem name and deprecation horizon to deprecation notifications.
588
+ * Add `before?` and `after?` methods to `Date`, `DateTime`,
589
+ `Time`, and `TimeWithZone`.
502
590
 
503
- *Willem van Bergen*
591
+ *Nick Holden*
504
592
 
505
- * Add support for `:offset` and `:zone` to `ActiveSupport::TimeWithZone#change`.
593
+ * `ActiveSupport::Inflector#ordinal` and `ActiveSupport::Inflector#ordinalize` now support
594
+ translations through I18n.
506
595
 
507
- *Andrew White*
596
+ # locale/fr.rb
508
597
 
509
- * Add support for `:offset` to `Time#change`.
598
+ {
599
+ fr: {
600
+ number: {
601
+ nth: {
602
+ ordinals: lambda do |_key, number:, **_options|
603
+ if number.to_i.abs == 1
604
+ 'er'
605
+ else
606
+ 'e'
607
+ end
608
+ end,
510
609
 
511
- Fixes #28723.
610
+ ordinalized: lambda do |_key, number:, **_options|
611
+ "#{number}#{ActiveSupport::Inflector.ordinal(number)}"
612
+ end
613
+ }
614
+ }
615
+ }
616
+ }
512
617
 
513
- *Andrew White*
514
618
 
515
- * Add `fetch_values` for `HashWithIndifferentAccess`.
619
+ *Christian Blais*
620
+
621
+ * Add `:private` option to ActiveSupport's `Module#delegate`
622
+ in order to delegate methods as private:
623
+
624
+ class User < ActiveRecord::Base
625
+ has_one :profile
626
+ delegate :date_of_birth, to: :profile, private: true
627
+
628
+ def age
629
+ Date.today.year - date_of_birth.year
630
+ end
631
+ end
632
+
633
+ # User.new.age # => 29
634
+ # User.new.date_of_birth
635
+ # => NoMethodError: private method `date_of_birth' called for #<User:0x00000008221340>
636
+
637
+ *Tomas Valent*
638
+
639
+ * `String#truncate_bytes` to truncate a string to a maximum bytesize without
640
+ breaking multibyte characters or grapheme clusters like 👩‍👩‍👦‍👦.
641
+
642
+ *Jeremy Daer*
643
+
644
+ * `String#strip_heredoc` preserves frozenness.
645
+
646
+ "foo".freeze.strip_heredoc.frozen? # => true
647
+
648
+ Fixes that frozen string literals would inadvertently become unfrozen:
649
+
650
+ # frozen_string_literal: true
651
+
652
+ foo = <<-MSG.strip_heredoc
653
+ la la la
654
+ MSG
655
+
656
+ foo.frozen? # => false !??
657
+
658
+ *Jeremy Daer*
659
+
660
+ * Rails 6 requires Ruby 2.5.0 or newer.
661
+
662
+ *Jeremy Daer*, *Kasper Timm Hansen*
663
+
664
+ * Adds parallel testing to Rails.
516
665
 
517
- The method was originally added to `Hash` in Ruby 2.3.0.
666
+ Parallelize your test suite with forked processes or threads.
518
667
 
519
- *Josh Pencheon*
668
+ *Eileen M. Uchitelle*, *Aaron Patterson*
520
669
 
521
670
 
522
- Please check [5-1-stable](https://github.com/rails/rails/blob/5-1-stable/activesupport/CHANGELOG.md) for previous changes.
671
+ Please check [5-2-stable](https://github.com/rails/rails/blob/5-2-stable/activesupport/CHANGELOG.md) for previous changes.