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,34 +1,40 @@
|
|
1
|
-
|
2
|
-
|
3
|
-
require
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "erb"
|
4
|
+
require "active_support/core_ext/kernel/singleton_class"
|
5
|
+
require "active_support/core_ext/module/redefine_method"
|
6
|
+
require "active_support/multibyte/unicode"
|
4
7
|
|
5
8
|
class ERB
|
6
9
|
module Util
|
7
|
-
HTML_ESCAPE = {
|
8
|
-
JSON_ESCAPE = {
|
9
|
-
HTML_ESCAPE_REGEXP = /[&"'><]/
|
10
|
+
HTML_ESCAPE = { "&" => "&", ">" => ">", "<" => "<", '"' => """, "'" => "'" }
|
11
|
+
JSON_ESCAPE = { "&" => '\u0026', ">" => '\u003e', "<" => '\u003c', "\u2028" => '\u2028', "\u2029" => '\u2029' }
|
10
12
|
HTML_ESCAPE_ONCE_REGEXP = /["><']|&(?!([a-zA-Z]+|(#\d+)|(#[xX][\dA-Fa-f]+));)/
|
11
13
|
JSON_ESCAPE_REGEXP = /[\u2028\u2029&><]/u
|
12
14
|
|
15
|
+
# Following XML requirements: https://www.w3.org/TR/REC-xml/#NT-Name
|
16
|
+
TAG_NAME_START_REGEXP_SET = "@:A-Z_a-z\u{C0}-\u{D6}\u{D8}-\u{F6}\u{F8}-\u{2FF}\u{370}-\u{37D}\u{37F}-\u{1FFF}" \
|
17
|
+
"\u{200C}-\u{200D}\u{2070}-\u{218F}\u{2C00}-\u{2FEF}\u{3001}-\u{D7FF}\u{F900}-\u{FDCF}" \
|
18
|
+
"\u{FDF0}-\u{FFFD}\u{10000}-\u{EFFFF}"
|
19
|
+
TAG_NAME_START_REGEXP = /[^#{TAG_NAME_START_REGEXP_SET}]/
|
20
|
+
TAG_NAME_FOLLOWING_REGEXP = /[^#{TAG_NAME_START_REGEXP_SET}\-.0-9\u{B7}\u{0300}-\u{036F}\u{203F}-\u{2040}]/
|
21
|
+
TAG_NAME_REPLACEMENT_CHAR = "_"
|
22
|
+
|
13
23
|
# A utility method for escaping HTML tag characters.
|
14
24
|
# This method is also aliased as <tt>h</tt>.
|
15
25
|
#
|
16
|
-
# In your ERB templates, use this method to escape any unsafe content. For example:
|
17
|
-
# <%=h @person.name %>
|
18
|
-
#
|
19
26
|
# puts html_escape('is a > 0 & a < 10?')
|
20
27
|
# # => is a > 0 & a < 10?
|
21
28
|
def html_escape(s)
|
22
29
|
unwrapped_html_escape(s).html_safe
|
23
30
|
end
|
24
31
|
|
25
|
-
|
26
|
-
remove_method(:h)
|
32
|
+
silence_redefinition_of_method :h
|
27
33
|
alias h html_escape
|
28
34
|
|
29
35
|
module_function :h
|
30
36
|
|
31
|
-
singleton_class.
|
37
|
+
singleton_class.silence_redefinition_of_method :html_escape
|
32
38
|
module_function :html_escape
|
33
39
|
|
34
40
|
# HTML escapes strings but doesn't wrap them with an ActiveSupport::SafeBuffer.
|
@@ -38,7 +44,7 @@ class ERB
|
|
38
44
|
if s.html_safe?
|
39
45
|
s
|
40
46
|
else
|
41
|
-
|
47
|
+
CGI.escapeHTML(ActiveSupport::Multibyte::Unicode.tidy_bytes(s))
|
42
48
|
end
|
43
49
|
end
|
44
50
|
module_function :unwrapped_html_escape
|
@@ -51,7 +57,7 @@ class ERB
|
|
51
57
|
# html_escape_once('<< Accept & Checkout')
|
52
58
|
# # => "<< Accept & Checkout"
|
53
59
|
def html_escape_once(s)
|
54
|
-
result = s.to_s.gsub(HTML_ESCAPE_ONCE_REGEXP, HTML_ESCAPE)
|
60
|
+
result = ActiveSupport::Multibyte::Unicode.tidy_bytes(s.to_s).gsub(HTML_ESCAPE_ONCE_REGEXP, HTML_ESCAPE)
|
55
61
|
s.html_safe? ? result.html_safe : result
|
56
62
|
end
|
57
63
|
|
@@ -86,6 +92,11 @@ class ERB
|
|
86
92
|
# automatically flag the result as HTML safe, since the raw value is unsafe to
|
87
93
|
# use inside HTML attributes.
|
88
94
|
#
|
95
|
+
# If your JSON is being used downstream for insertion into the DOM, be aware of
|
96
|
+
# whether or not it is being inserted via +html()+. Most jQuery plugins do this.
|
97
|
+
# If that is the case, be sure to +html_escape+ or +sanitize+ any user-generated
|
98
|
+
# content returned by your JSON.
|
99
|
+
#
|
89
100
|
# If you need to output JSON elsewhere in your HTML, you can just do something
|
90
101
|
# like this, as any unsafe characters (including quotation marks) will be
|
91
102
|
# automatically escaped for you:
|
@@ -113,6 +124,26 @@ class ERB
|
|
113
124
|
end
|
114
125
|
|
115
126
|
module_function :json_escape
|
127
|
+
|
128
|
+
# A utility method for escaping XML names of tags and names of attributes.
|
129
|
+
#
|
130
|
+
# xml_name_escape('1 < 2 & 3')
|
131
|
+
# # => "1___2___3"
|
132
|
+
#
|
133
|
+
# It follows the requirements of the specification: https://www.w3.org/TR/REC-xml/#NT-Name
|
134
|
+
def xml_name_escape(name)
|
135
|
+
name = name.to_s
|
136
|
+
return "" if name.blank?
|
137
|
+
|
138
|
+
starting_char = name[0].gsub(TAG_NAME_START_REGEXP, TAG_NAME_REPLACEMENT_CHAR)
|
139
|
+
|
140
|
+
return starting_char if name.size == 1
|
141
|
+
|
142
|
+
following_chars = name[1..-1].gsub(TAG_NAME_FOLLOWING_REGEXP, TAG_NAME_REPLACEMENT_CHAR)
|
143
|
+
|
144
|
+
starting_char + following_chars
|
145
|
+
end
|
146
|
+
module_function :xml_name_escape
|
116
147
|
end
|
117
148
|
end
|
118
149
|
|
@@ -138,27 +169,26 @@ module ActiveSupport #:nodoc:
|
|
138
169
|
alias_method :original_concat, :concat
|
139
170
|
private :original_concat
|
140
171
|
|
172
|
+
# Raised when <tt>ActiveSupport::SafeBuffer#safe_concat</tt> is called on unsafe buffers.
|
141
173
|
class SafeConcatError < StandardError
|
142
174
|
def initialize
|
143
|
-
super
|
175
|
+
super "Could not concatenate to the buffer because it is not html safe."
|
144
176
|
end
|
145
177
|
end
|
146
178
|
|
147
179
|
def [](*args)
|
148
180
|
if args.size < 2
|
149
181
|
super
|
150
|
-
|
151
|
-
|
152
|
-
new_safe_buffer = super
|
182
|
+
elsif html_safe?
|
183
|
+
new_safe_buffer = super
|
153
184
|
|
154
|
-
|
155
|
-
|
156
|
-
end
|
157
|
-
|
158
|
-
new_safe_buffer
|
159
|
-
else
|
160
|
-
to_str[*args]
|
185
|
+
if new_safe_buffer
|
186
|
+
new_safe_buffer.instance_variable_set :@html_safe, true
|
161
187
|
end
|
188
|
+
|
189
|
+
new_safe_buffer
|
190
|
+
else
|
191
|
+
to_str[*args]
|
162
192
|
end
|
163
193
|
end
|
164
194
|
|
@@ -167,7 +197,7 @@ module ActiveSupport #:nodoc:
|
|
167
197
|
original_concat(value)
|
168
198
|
end
|
169
199
|
|
170
|
-
def initialize(
|
200
|
+
def initialize(str = "")
|
171
201
|
@html_safe = true
|
172
202
|
super
|
173
203
|
end
|
@@ -190,11 +220,6 @@ module ActiveSupport #:nodoc:
|
|
190
220
|
super(html_escape_interpolated_argument(value))
|
191
221
|
end
|
192
222
|
|
193
|
-
def prepend!(value)
|
194
|
-
ActiveSupport::Deprecation.deprecation_warning "ActiveSupport::SafeBuffer#prepend!", :prepend
|
195
|
-
prepend value
|
196
|
-
end
|
197
|
-
|
198
223
|
def +(other)
|
199
224
|
dup.concat(other)
|
200
225
|
end
|
@@ -202,7 +227,7 @@ module ActiveSupport #:nodoc:
|
|
202
227
|
def %(args)
|
203
228
|
case args
|
204
229
|
when Hash
|
205
|
-
escaped_args = Hash[args.map { |k,arg| [k, html_escape_interpolated_argument(arg)] }]
|
230
|
+
escaped_args = Hash[args.map { |k, arg| [k, html_escape_interpolated_argument(arg)] }]
|
206
231
|
else
|
207
232
|
escaped_args = Array(args).map { |arg| html_escape_interpolated_argument(arg) }
|
208
233
|
end
|
@@ -243,18 +268,17 @@ module ActiveSupport #:nodoc:
|
|
243
268
|
|
244
269
|
private
|
245
270
|
|
246
|
-
|
247
|
-
|
248
|
-
|
249
|
-
end
|
271
|
+
def html_escape_interpolated_argument(arg)
|
272
|
+
(!html_safe? || arg.html_safe?) ? arg : CGI.escapeHTML(arg.to_s)
|
273
|
+
end
|
250
274
|
end
|
251
275
|
end
|
252
276
|
|
253
277
|
class String
|
254
278
|
# Marks a string as trusted safe. It will be inserted into HTML with no
|
255
|
-
# additional escaping performed. It is your
|
279
|
+
# additional escaping performed. It is your responsibility to ensure that the
|
256
280
|
# string contains no malicious content. This method is equivalent to the
|
257
|
-
#
|
281
|
+
# +raw+ helper in views. It is recommended that you use +sanitize+ instead of
|
258
282
|
# this method. It should never be called on user input.
|
259
283
|
def html_safe
|
260
284
|
ActiveSupport::SafeBuffer.new(self)
|
@@ -1,4 +1,4 @@
|
|
1
|
-
|
1
|
+
# frozen_string_literal: true
|
2
2
|
|
3
3
|
class String
|
4
4
|
# Strips indentation in heredocs.
|
@@ -17,10 +17,9 @@ class String
|
|
17
17
|
#
|
18
18
|
# the user would see the usage message aligned against the left margin.
|
19
19
|
#
|
20
|
-
# Technically, it looks for the least indented line
|
21
|
-
# that amount of leading whitespace.
|
20
|
+
# Technically, it looks for the least indented non-empty line
|
21
|
+
# in the whole string, and removes that amount of leading whitespace.
|
22
22
|
def strip_heredoc
|
23
|
-
|
24
|
-
gsub(/^[ \t]{#{indent}}/, '')
|
23
|
+
gsub(/^#{scan(/^[ \t]*(?=\S)/).min}/, "".freeze)
|
25
24
|
end
|
26
25
|
end
|
@@ -1,5 +1,7 @@
|
|
1
|
-
|
2
|
-
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "active_support/core_ext/string/conversions"
|
4
|
+
require "active_support/core_ext/time/zones"
|
3
5
|
|
4
6
|
class String
|
5
7
|
# Converts String to a TimeWithZone in the current zone if Time.zone or Time.zone_default
|
@@ -1,13 +1,15 @@
|
|
1
|
-
|
2
|
-
|
3
|
-
require
|
4
|
-
require
|
5
|
-
require
|
6
|
-
require
|
7
|
-
require
|
8
|
-
require
|
9
|
-
require
|
10
|
-
require
|
11
|
-
require
|
12
|
-
require
|
13
|
-
require
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "active_support/core_ext/string/conversions"
|
4
|
+
require "active_support/core_ext/string/filters"
|
5
|
+
require "active_support/core_ext/string/multibyte"
|
6
|
+
require "active_support/core_ext/string/starts_ends_with"
|
7
|
+
require "active_support/core_ext/string/inflections"
|
8
|
+
require "active_support/core_ext/string/access"
|
9
|
+
require "active_support/core_ext/string/behavior"
|
10
|
+
require "active_support/core_ext/string/output_safety"
|
11
|
+
require "active_support/core_ext/string/exclude"
|
12
|
+
require "active_support/core_ext/string/strip"
|
13
|
+
require "active_support/core_ext/string/inquiry"
|
14
|
+
require "active_support/core_ext/string/indent"
|
15
|
+
require "active_support/core_ext/string/zones"
|
@@ -1,9 +1,11 @@
|
|
1
|
-
|
2
|
-
|
3
|
-
require
|
4
|
-
require
|
5
|
-
require
|
6
|
-
require
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "active_support/duration"
|
4
|
+
require "active_support/core_ext/time/conversions"
|
5
|
+
require "active_support/time_with_zone"
|
6
|
+
require "active_support/core_ext/time/zones"
|
7
|
+
require "active_support/core_ext/date_and_time/calculations"
|
8
|
+
require "active_support/core_ext/date/calculations"
|
7
9
|
|
8
10
|
class Time
|
9
11
|
include DateAndTime::Calculations
|
@@ -16,9 +18,9 @@ class Time
|
|
16
18
|
super || (self == Time && other.is_a?(ActiveSupport::TimeWithZone))
|
17
19
|
end
|
18
20
|
|
19
|
-
#
|
21
|
+
# Returns the number of days in the given month.
|
20
22
|
# If no year is specified, it will use the current year.
|
21
|
-
def days_in_month(month, year =
|
23
|
+
def days_in_month(month, year = current.year)
|
22
24
|
if month == 2 && ::Date.gregorian_leap?(year)
|
23
25
|
29
|
24
26
|
else
|
@@ -26,6 +28,12 @@ class Time
|
|
26
28
|
end
|
27
29
|
end
|
28
30
|
|
31
|
+
# Returns the number of days in the given year.
|
32
|
+
# If no year is specified, it will use the current year.
|
33
|
+
def days_in_year(year = current.year)
|
34
|
+
days_in_month(2, year) + 337
|
35
|
+
end
|
36
|
+
|
29
37
|
# Returns <tt>Time.zone.now</tt> when <tt>Time.zone</tt> or <tt>config.time_zone</tt> are set, otherwise just returns <tt>Time.now</tt>.
|
30
38
|
def current
|
31
39
|
::Time.zone ? ::Time.zone.now : ::Time.now
|
@@ -47,11 +55,38 @@ class Time
|
|
47
55
|
end
|
48
56
|
alias_method :at_without_coercion, :at
|
49
57
|
alias_method :at, :at_with_coercion
|
58
|
+
|
59
|
+
# Creates a +Time+ instance from an RFC 3339 string.
|
60
|
+
#
|
61
|
+
# Time.rfc3339('1999-12-31T14:00:00-10:00') # => 2000-01-01 00:00:00 -1000
|
62
|
+
#
|
63
|
+
# If the time or offset components are missing then an +ArgumentError+ will be raised.
|
64
|
+
#
|
65
|
+
# Time.rfc3339('1999-12-31') # => ArgumentError: invalid date
|
66
|
+
def rfc3339(str)
|
67
|
+
parts = Date._rfc3339(str)
|
68
|
+
|
69
|
+
raise ArgumentError, "invalid date" if parts.empty?
|
70
|
+
|
71
|
+
Time.new(
|
72
|
+
parts.fetch(:year),
|
73
|
+
parts.fetch(:mon),
|
74
|
+
parts.fetch(:mday),
|
75
|
+
parts.fetch(:hour),
|
76
|
+
parts.fetch(:min),
|
77
|
+
parts.fetch(:sec) + parts.fetch(:sec_fraction, 0),
|
78
|
+
parts.fetch(:offset)
|
79
|
+
)
|
80
|
+
end
|
50
81
|
end
|
51
82
|
|
52
|
-
#
|
83
|
+
# Returns the number of seconds since 00:00:00.
|
84
|
+
#
|
85
|
+
# Time.new(2012, 8, 29, 0, 0, 0).seconds_since_midnight # => 0.0
|
86
|
+
# Time.new(2012, 8, 29, 12, 34, 56).seconds_since_midnight # => 45296.0
|
87
|
+
# Time.new(2012, 8, 29, 23, 59, 59).seconds_since_midnight # => 86399.0
|
53
88
|
def seconds_since_midnight
|
54
|
-
to_i - change(:
|
89
|
+
to_i - change(hour: 0).to_i + (usec / 1.0e+6)
|
55
90
|
end
|
56
91
|
|
57
92
|
# Returns the number of seconds until 23:59:59.
|
@@ -74,36 +109,42 @@ class Time
|
|
74
109
|
# to the +options+ parameter. The time options (<tt>:hour</tt>, <tt>:min</tt>,
|
75
110
|
# <tt>:sec</tt>, <tt>:usec</tt>, <tt>:nsec</tt>) reset cascadingly, so if only
|
76
111
|
# the hour is passed, then minute, sec, usec and nsec is set to 0. If the hour
|
77
|
-
# and minute is passed, then sec, usec and nsec is set to 0. The +options+
|
78
|
-
#
|
79
|
-
# <tt>:
|
80
|
-
# <tt>:
|
112
|
+
# and minute is passed, then sec, usec and nsec is set to 0. The +options+ parameter
|
113
|
+
# takes a hash with any of these keys: <tt>:year</tt>, <tt>:month</tt>, <tt>:day</tt>,
|
114
|
+
# <tt>:hour</tt>, <tt>:min</tt>, <tt>:sec</tt>, <tt>:usec</tt>, <tt>:nsec</tt>,
|
115
|
+
# <tt>:offset</tt>. Pass either <tt>:usec</tt> or <tt>:nsec</tt>, not both.
|
81
116
|
#
|
82
117
|
# Time.new(2012, 8, 29, 22, 35, 0).change(day: 1) # => Time.new(2012, 8, 1, 22, 35, 0)
|
83
118
|
# Time.new(2012, 8, 29, 22, 35, 0).change(year: 1981, day: 1) # => Time.new(1981, 8, 1, 22, 35, 0)
|
84
119
|
# Time.new(2012, 8, 29, 22, 35, 0).change(year: 1981, hour: 0) # => Time.new(1981, 8, 29, 0, 0, 0)
|
85
120
|
def change(options)
|
86
|
-
new_year
|
87
|
-
new_month
|
88
|
-
new_day
|
89
|
-
new_hour
|
90
|
-
new_min
|
91
|
-
new_sec
|
121
|
+
new_year = options.fetch(:year, year)
|
122
|
+
new_month = options.fetch(:month, month)
|
123
|
+
new_day = options.fetch(:day, day)
|
124
|
+
new_hour = options.fetch(:hour, hour)
|
125
|
+
new_min = options.fetch(:min, options[:hour] ? 0 : min)
|
126
|
+
new_sec = options.fetch(:sec, (options[:hour] || options[:min]) ? 0 : sec)
|
127
|
+
new_offset = options.fetch(:offset, nil)
|
92
128
|
|
93
129
|
if new_nsec = options[:nsec]
|
94
130
|
raise ArgumentError, "Can't change both :nsec and :usec at the same time: #{options.inspect}" if options[:usec]
|
95
131
|
new_usec = Rational(new_nsec, 1000)
|
96
132
|
else
|
97
|
-
new_usec
|
133
|
+
new_usec = options.fetch(:usec, (options[:hour] || options[:min] || options[:sec]) ? 0 : Rational(nsec, 1000))
|
98
134
|
end
|
99
135
|
|
100
|
-
if
|
101
|
-
|
136
|
+
raise ArgumentError, "argument out of range" if new_usec >= 1000000
|
137
|
+
|
138
|
+
new_sec += Rational(new_usec, 1000000)
|
139
|
+
|
140
|
+
if new_offset
|
141
|
+
::Time.new(new_year, new_month, new_day, new_hour, new_min, new_sec, new_offset)
|
142
|
+
elsif utc?
|
143
|
+
::Time.utc(new_year, new_month, new_day, new_hour, new_min, new_sec)
|
102
144
|
elsif zone
|
103
|
-
::Time.local(new_year, new_month, new_day, new_hour, new_min, new_sec
|
145
|
+
::Time.local(new_year, new_month, new_day, new_hour, new_min, new_sec)
|
104
146
|
else
|
105
|
-
|
106
|
-
::Time.new(new_year, new_month, new_day, new_hour, new_min, new_sec + (new_usec.to_r / 1000000), utc_offset)
|
147
|
+
::Time.new(new_year, new_month, new_day, new_hour, new_min, new_sec, utc_offset)
|
107
148
|
end
|
108
149
|
end
|
109
150
|
|
@@ -131,7 +172,7 @@ class Time
|
|
131
172
|
|
132
173
|
d = to_date.advance(options)
|
133
174
|
d = d.gregorian if d.julian?
|
134
|
-
time_advanced_by_date = change(:
|
175
|
+
time_advanced_by_date = change(year: d.year, month: d.month, day: d.day)
|
135
176
|
seconds_to_advance = \
|
136
177
|
options.fetch(:seconds, 0) +
|
137
178
|
options.fetch(:minutes, 0) * 60 +
|
@@ -159,8 +200,7 @@ class Time
|
|
159
200
|
|
160
201
|
# Returns a new Time representing the start of the day (0:00)
|
161
202
|
def beginning_of_day
|
162
|
-
|
163
|
-
change(:hour => 0)
|
203
|
+
change(hour: 0)
|
164
204
|
end
|
165
205
|
alias :midnight :beginning_of_day
|
166
206
|
alias :at_midnight :beginning_of_day
|
@@ -168,7 +208,7 @@ class Time
|
|
168
208
|
|
169
209
|
# Returns a new Time representing the middle of the day (12:00)
|
170
210
|
def middle_of_day
|
171
|
-
change(:
|
211
|
+
change(hour: 12)
|
172
212
|
end
|
173
213
|
alias :midday :middle_of_day
|
174
214
|
alias :noon :middle_of_day
|
@@ -176,53 +216,48 @@ class Time
|
|
176
216
|
alias :at_noon :middle_of_day
|
177
217
|
alias :at_middle_of_day :middle_of_day
|
178
218
|
|
179
|
-
# Returns a new Time representing the end of the day, 23:59:59.999999
|
219
|
+
# Returns a new Time representing the end of the day, 23:59:59.999999
|
180
220
|
def end_of_day
|
181
221
|
change(
|
182
|
-
:
|
183
|
-
:
|
184
|
-
:
|
185
|
-
:
|
222
|
+
hour: 23,
|
223
|
+
min: 59,
|
224
|
+
sec: 59,
|
225
|
+
usec: Rational(999999999, 1000)
|
186
226
|
)
|
187
227
|
end
|
188
228
|
alias :at_end_of_day :end_of_day
|
189
229
|
|
190
230
|
# Returns a new Time representing the start of the hour (x:00)
|
191
231
|
def beginning_of_hour
|
192
|
-
change(:
|
232
|
+
change(min: 0)
|
193
233
|
end
|
194
234
|
alias :at_beginning_of_hour :beginning_of_hour
|
195
235
|
|
196
|
-
# Returns a new Time representing the end of the hour, x:59:59.999999
|
236
|
+
# Returns a new Time representing the end of the hour, x:59:59.999999
|
197
237
|
def end_of_hour
|
198
238
|
change(
|
199
|
-
:
|
200
|
-
:
|
201
|
-
:
|
239
|
+
min: 59,
|
240
|
+
sec: 59,
|
241
|
+
usec: Rational(999999999, 1000)
|
202
242
|
)
|
203
243
|
end
|
204
244
|
alias :at_end_of_hour :end_of_hour
|
205
245
|
|
206
246
|
# Returns a new Time representing the start of the minute (x:xx:00)
|
207
247
|
def beginning_of_minute
|
208
|
-
change(:
|
248
|
+
change(sec: 0)
|
209
249
|
end
|
210
250
|
alias :at_beginning_of_minute :beginning_of_minute
|
211
251
|
|
212
|
-
# Returns a new Time representing the end of the minute, x:xx:59.999999
|
252
|
+
# Returns a new Time representing the end of the minute, x:xx:59.999999
|
213
253
|
def end_of_minute
|
214
254
|
change(
|
215
|
-
:
|
216
|
-
:
|
255
|
+
sec: 59,
|
256
|
+
usec: Rational(999999999, 1000)
|
217
257
|
)
|
218
258
|
end
|
219
259
|
alias :at_end_of_minute :end_of_minute
|
220
260
|
|
221
|
-
# Returns a Range representing the whole day of the current time.
|
222
|
-
def all_day
|
223
|
-
beginning_of_day..end_of_day
|
224
|
-
end
|
225
|
-
|
226
261
|
def plus_with_duration(other) #:nodoc:
|
227
262
|
if ActiveSupport::Duration === other
|
228
263
|
other.since(self)
|
@@ -256,7 +291,7 @@ class Time
|
|
256
291
|
# Layers additional behavior on Time#<=> so that DateTime and ActiveSupport::TimeWithZone instances
|
257
292
|
# can be chronologically compared with a Time
|
258
293
|
def compare_with_coercion(other)
|
259
|
-
# we're avoiding Time#to_datetime
|
294
|
+
# we're avoiding Time#to_datetime and Time#to_time because they're expensive
|
260
295
|
if other.class == Time
|
261
296
|
compare_without_coercion(other)
|
262
297
|
elsif other.is_a?(Time)
|
@@ -277,5 +312,4 @@ class Time
|
|
277
312
|
end
|
278
313
|
alias_method :eql_without_coercion, :eql?
|
279
314
|
alias_method :eql?, :eql_with_coercion
|
280
|
-
|
281
315
|
end
|
@@ -1,10 +1,12 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
require "active_support/core_ext/date_and_time/compatibility"
|
2
|
-
require "active_support/core_ext/module/
|
4
|
+
require "active_support/core_ext/module/redefine_method"
|
3
5
|
|
4
6
|
class Time
|
5
7
|
include DateAndTime::Compatibility
|
6
8
|
|
7
|
-
|
9
|
+
silence_redefinition_of_method :to_time
|
8
10
|
|
9
11
|
# Either return +self+ or the time in the local system timezone depending
|
10
12
|
# on the setting of +ActiveSupport.to_time_preserves_timezone+.
|
@@ -1,30 +1,33 @@
|
|
1
|
-
|
2
|
-
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "active_support/inflector/methods"
|
4
|
+
require "active_support/values/time_zone"
|
3
5
|
|
4
6
|
class Time
|
5
7
|
DATE_FORMATS = {
|
6
|
-
:
|
7
|
-
:
|
8
|
-
:
|
9
|
-
:
|
10
|
-
:
|
11
|
-
:
|
12
|
-
:
|
8
|
+
db: "%Y-%m-%d %H:%M:%S",
|
9
|
+
number: "%Y%m%d%H%M%S",
|
10
|
+
nsec: "%Y%m%d%H%M%S%9N",
|
11
|
+
usec: "%Y%m%d%H%M%S%6N",
|
12
|
+
time: "%H:%M",
|
13
|
+
short: "%d %b %H:%M",
|
14
|
+
long: "%B %d, %Y %H:%M",
|
15
|
+
long_ordinal: lambda { |time|
|
13
16
|
day_format = ActiveSupport::Inflector.ordinalize(time.day)
|
14
17
|
time.strftime("%B #{day_format}, %Y %H:%M")
|
15
18
|
},
|
16
|
-
:
|
19
|
+
rfc822: lambda { |time|
|
17
20
|
offset_format = time.formatted_offset(false)
|
18
21
|
time.strftime("%a, %d %b %Y %H:%M:%S #{offset_format}")
|
19
22
|
},
|
20
|
-
:
|
23
|
+
iso8601: lambda { |time| time.iso8601 }
|
21
24
|
}
|
22
25
|
|
23
26
|
# Converts to a formatted string. See DATE_FORMATS for built-in formats.
|
24
27
|
#
|
25
28
|
# This method is aliased to <tt>to_s</tt>.
|
26
29
|
#
|
27
|
-
# time = Time.now # =>
|
30
|
+
# time = Time.now # => 2007-01-18 06:10:17 -06:00
|
28
31
|
#
|
29
32
|
# time.to_formatted_s(:time) # => "06:10"
|
30
33
|
# time.to_s(:time) # => "06:10"
|
@@ -55,11 +58,15 @@ class Time
|
|
55
58
|
alias_method :to_default_s, :to_s
|
56
59
|
alias_method :to_s, :to_formatted_s
|
57
60
|
|
58
|
-
# Returns the
|
61
|
+
# Returns a formatted string of the offset from UTC, or an alternative
|
62
|
+
# string if the time zone is already UTC.
|
59
63
|
#
|
60
64
|
# Time.local(2000).formatted_offset # => "-06:00"
|
61
65
|
# Time.local(2000).formatted_offset(false) # => "-0600"
|
62
66
|
def formatted_offset(colon = true, alternate_utc_string = nil)
|
63
67
|
utc? && alternate_utc_string || ActiveSupport::TimeZone.seconds_to_utc_offset(utc_offset, colon)
|
64
68
|
end
|
69
|
+
|
70
|
+
# Aliased to +xmlschema+ for compatibility with +DateTime+
|
71
|
+
alias_method :rfc3339, :xmlschema
|
65
72
|
end
|