activesupport 5.1.7 → 7.0.4.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 +259 -585
- data/MIT-LICENSE +1 -1
- data/README.rdoc +6 -5
- data/lib/active_support/actionable_error.rb +48 -0
- data/lib/active_support/all.rb +2 -0
- data/lib/active_support/array_inquirer.rb +4 -2
- data/lib/active_support/backtrace_cleaner.rb +33 -5
- data/lib/active_support/benchmarkable.rb +5 -3
- data/lib/active_support/builder.rb +2 -0
- data/lib/active_support/cache/file_store.rb +50 -43
- data/lib/active_support/cache/mem_cache_store.rb +194 -67
- data/lib/active_support/cache/memory_store.rb +70 -34
- data/lib/active_support/cache/null_store.rb +18 -3
- data/lib/active_support/cache/redis_cache_store.rb +474 -0
- data/lib/active_support/cache/strategy/local_cache.rb +73 -50
- data/lib/active_support/cache/strategy/local_cache_middleware.rb +2 -0
- data/lib/active_support/cache.rb +556 -220
- data/lib/active_support/callbacks.rb +264 -159
- data/lib/active_support/code_generator.rb +65 -0
- data/lib/active_support/concern.rb +81 -8
- data/lib/active_support/concurrency/load_interlock_aware_monitor.rb +16 -0
- data/lib/active_support/concurrency/share_lock.rb +4 -3
- data/lib/active_support/configurable.rb +17 -16
- data/lib/active_support/configuration_file.rb +51 -0
- data/lib/active_support/core_ext/array/access.rb +18 -8
- data/lib/active_support/core_ext/array/conversions.rb +20 -17
- data/lib/active_support/core_ext/array/deprecated_conversions.rb +25 -0
- data/lib/active_support/core_ext/array/extract.rb +21 -0
- data/lib/active_support/core_ext/array/extract_options.rb +2 -0
- data/lib/active_support/core_ext/array/grouping.rb +8 -6
- data/lib/active_support/core_ext/array/inquiry.rb +4 -2
- data/lib/active_support/core_ext/array/wrap.rb +2 -0
- data/lib/active_support/core_ext/array.rb +4 -1
- data/lib/active_support/core_ext/benchmark.rb +4 -2
- data/lib/active_support/core_ext/big_decimal/conversions.rb +3 -1
- data/lib/active_support/core_ext/big_decimal.rb +2 -0
- data/lib/active_support/core_ext/class/attribute.rb +50 -47
- data/lib/active_support/core_ext/class/attribute_accessors.rb +2 -0
- data/lib/active_support/core_ext/class/subclasses.rb +10 -24
- data/lib/active_support/core_ext/class.rb +2 -0
- data/lib/active_support/core_ext/date/acts_like.rb +2 -0
- data/lib/active_support/core_ext/date/blank.rb +3 -1
- data/lib/active_support/core_ext/date/calculations.rb +17 -14
- data/lib/active_support/core_ext/date/conversions.rb +24 -22
- data/lib/active_support/core_ext/date/deprecated_conversions.rb +26 -0
- data/lib/active_support/core_ext/date/zones.rb +2 -0
- data/lib/active_support/core_ext/date.rb +3 -0
- data/lib/active_support/core_ext/date_and_time/calculations.rb +65 -41
- data/lib/active_support/core_ext/date_and_time/compatibility.rb +18 -1
- data/lib/active_support/core_ext/date_and_time/zones.rb +2 -1
- data/lib/active_support/core_ext/date_time/acts_like.rb +2 -0
- data/lib/active_support/core_ext/date_time/blank.rb +3 -1
- data/lib/active_support/core_ext/date_time/calculations.rb +3 -1
- data/lib/active_support/core_ext/date_time/compatibility.rb +7 -5
- data/lib/active_support/core_ext/date_time/conversions.rb +15 -14
- data/lib/active_support/core_ext/date_time/deprecated_conversions.rb +22 -0
- data/lib/active_support/core_ext/date_time.rb +3 -0
- data/lib/active_support/core_ext/digest/uuid.rb +42 -14
- data/lib/active_support/core_ext/digest.rb +3 -0
- data/lib/active_support/core_ext/enumerable.rb +244 -72
- data/lib/active_support/core_ext/file/atomic.rb +6 -2
- data/lib/active_support/core_ext/file.rb +2 -0
- data/lib/active_support/core_ext/hash/conversions.rb +7 -6
- data/lib/active_support/core_ext/hash/deep_merge.rb +8 -12
- data/lib/active_support/core_ext/hash/deep_transform_values.rb +46 -0
- data/lib/active_support/core_ext/hash/except.rb +4 -2
- data/lib/active_support/core_ext/hash/indifferent_access.rb +5 -3
- data/lib/active_support/core_ext/hash/keys.rb +4 -31
- data/lib/active_support/core_ext/hash/reverse_merge.rb +5 -2
- data/lib/active_support/core_ext/hash/slice.rb +8 -29
- data/lib/active_support/core_ext/hash.rb +3 -2
- data/lib/active_support/core_ext/integer/inflections.rb +2 -0
- data/lib/active_support/core_ext/integer/multiple.rb +3 -1
- data/lib/active_support/core_ext/integer/time.rb +7 -14
- data/lib/active_support/core_ext/integer.rb +2 -0
- data/lib/active_support/core_ext/kernel/concern.rb +2 -0
- data/lib/active_support/core_ext/kernel/reporting.rb +6 -4
- data/lib/active_support/core_ext/kernel/singleton_class.rb +3 -1
- data/lib/active_support/core_ext/kernel.rb +2 -1
- data/lib/active_support/core_ext/load_error.rb +3 -8
- data/lib/active_support/core_ext/module/aliasing.rb +2 -0
- data/lib/active_support/core_ext/module/anonymous.rb +2 -0
- data/lib/active_support/core_ext/module/attr_internal.rb +4 -2
- data/lib/active_support/core_ext/module/attribute_accessors.rb +46 -56
- data/lib/active_support/core_ext/module/attribute_accessors_per_thread.rb +36 -27
- data/lib/active_support/core_ext/module/concerning.rb +15 -10
- data/lib/active_support/core_ext/module/delegation.rb +97 -58
- data/lib/active_support/core_ext/module/deprecation.rb +2 -0
- data/lib/active_support/core_ext/module/introspection.rb +18 -15
- data/lib/active_support/core_ext/module/redefine_method.rb +40 -0
- data/lib/active_support/core_ext/module/remove_method.rb +5 -23
- data/lib/active_support/core_ext/module.rb +3 -1
- data/lib/active_support/core_ext/name_error.rb +30 -2
- data/lib/active_support/core_ext/numeric/bytes.rb +2 -0
- data/lib/active_support/core_ext/numeric/conversions.rb +134 -129
- data/lib/active_support/core_ext/numeric/deprecated_conversions.rb +60 -0
- data/lib/active_support/core_ext/numeric/time.rb +7 -15
- data/lib/active_support/core_ext/numeric.rb +3 -1
- data/lib/active_support/core_ext/object/acts_like.rb +41 -6
- data/lib/active_support/core_ext/object/blank.rb +15 -5
- data/lib/active_support/core_ext/object/conversions.rb +2 -0
- data/lib/active_support/core_ext/object/deep_dup.rb +3 -1
- data/lib/active_support/core_ext/object/duplicable.rb +16 -110
- data/lib/active_support/core_ext/object/inclusion.rb +2 -0
- data/lib/active_support/core_ext/object/instance_variables.rb +2 -0
- data/lib/active_support/core_ext/object/json.rb +51 -26
- data/lib/active_support/core_ext/object/to_param.rb +2 -0
- data/lib/active_support/core_ext/object/to_query.rb +4 -2
- data/lib/active_support/core_ext/object/try.rb +26 -14
- data/lib/active_support/core_ext/object/with_options.rb +24 -3
- data/lib/active_support/core_ext/object.rb +2 -0
- data/lib/active_support/core_ext/pathname/existence.rb +21 -0
- data/lib/active_support/core_ext/pathname.rb +3 -0
- data/lib/active_support/core_ext/range/compare_range.rb +57 -0
- data/lib/active_support/core_ext/range/conversions.rb +35 -25
- data/lib/active_support/core_ext/range/deprecated_conversions.rb +26 -0
- data/lib/active_support/core_ext/range/each.rb +6 -3
- data/lib/active_support/core_ext/range/include_time_with_zone.rb +7 -0
- data/lib/active_support/core_ext/range/overlaps.rb +3 -1
- data/lib/active_support/core_ext/range.rb +4 -1
- data/lib/active_support/core_ext/regexp.rb +10 -5
- data/lib/active_support/core_ext/securerandom.rb +25 -3
- data/lib/active_support/core_ext/string/access.rb +7 -16
- data/lib/active_support/core_ext/string/behavior.rb +2 -0
- data/lib/active_support/core_ext/string/conversions.rb +5 -2
- data/lib/active_support/core_ext/string/exclude.rb +2 -0
- data/lib/active_support/core_ext/string/filters.rb +44 -1
- data/lib/active_support/core_ext/string/indent.rb +2 -0
- data/lib/active_support/core_ext/string/inflections.rb +69 -16
- data/lib/active_support/core_ext/string/inquiry.rb +4 -1
- data/lib/active_support/core_ext/string/multibyte.rb +9 -4
- data/lib/active_support/core_ext/string/output_safety.rb +135 -27
- data/lib/active_support/core_ext/string/starts_ends_with.rb +4 -2
- data/lib/active_support/core_ext/string/strip.rb +5 -1
- data/lib/active_support/core_ext/string/zones.rb +2 -0
- data/lib/active_support/core_ext/string.rb +2 -0
- data/lib/active_support/core_ext/symbol/starts_ends_with.rb +6 -0
- data/lib/active_support/core_ext/symbol.rb +3 -0
- data/lib/active_support/core_ext/time/acts_like.rb +2 -0
- data/lib/active_support/core_ext/time/calculations.rb +81 -24
- data/lib/active_support/core_ext/time/compatibility.rb +4 -2
- data/lib/active_support/core_ext/time/conversions.rb +17 -12
- data/lib/active_support/core_ext/time/deprecated_conversions.rb +22 -0
- data/lib/active_support/core_ext/time/zones.rb +12 -25
- data/lib/active_support/core_ext/time.rb +3 -0
- data/lib/active_support/core_ext/uri.rb +4 -23
- data/lib/active_support/core_ext.rb +4 -1
- data/lib/active_support/current_attributes/test_helper.rb +13 -0
- data/lib/active_support/current_attributes.rb +226 -0
- data/lib/active_support/dependencies/autoload.rb +2 -0
- data/lib/active_support/dependencies/interlock.rb +12 -18
- data/lib/active_support/dependencies/require_dependency.rb +28 -0
- data/lib/active_support/dependencies.rb +59 -715
- data/lib/active_support/deprecation/behaviors.rb +48 -13
- data/lib/active_support/deprecation/constant_accessor.rb +4 -2
- data/lib/active_support/deprecation/disallowed.rb +56 -0
- data/lib/active_support/deprecation/instance_delegator.rb +2 -1
- data/lib/active_support/deprecation/method_wrappers.rb +29 -21
- data/lib/active_support/deprecation/proxy_wrappers.rb +34 -8
- data/lib/active_support/deprecation/reporting.rb +54 -9
- data/lib/active_support/deprecation.rb +10 -3
- data/lib/active_support/descendants_tracker.rb +192 -34
- data/lib/active_support/digest.rb +22 -0
- data/lib/active_support/duration/iso8601_parser.rb +9 -9
- data/lib/active_support/duration/iso8601_serializer.rb +29 -15
- data/lib/active_support/duration.rb +158 -72
- data/lib/active_support/encrypted_configuration.rb +56 -0
- data/lib/active_support/encrypted_file.rb +129 -0
- data/lib/active_support/environment_inquirer.rb +20 -0
- data/lib/active_support/error_reporter.rb +117 -0
- data/lib/active_support/evented_file_update_checker.rb +87 -122
- data/lib/active_support/execution_context/test_helper.rb +13 -0
- data/lib/active_support/execution_context.rb +53 -0
- data/lib/active_support/execution_wrapper.rb +46 -21
- data/lib/active_support/executor/test_helper.rb +7 -0
- data/lib/active_support/executor.rb +2 -0
- data/lib/active_support/file_update_checker.rb +2 -1
- data/lib/active_support/fork_tracker.rb +71 -0
- data/lib/active_support/gem_version.rb +7 -5
- data/lib/active_support/gzip.rb +2 -0
- data/lib/active_support/hash_with_indifferent_access.rb +126 -42
- data/lib/active_support/html_safe_translation.rb +43 -0
- data/lib/active_support/i18n.rb +5 -1
- data/lib/active_support/i18n_railtie.rb +19 -14
- data/lib/active_support/inflections.rb +2 -0
- data/lib/active_support/inflector/inflections.rb +41 -14
- data/lib/active_support/inflector/methods.rb +73 -87
- data/lib/active_support/inflector/transliterate.rb +56 -18
- data/lib/active_support/inflector.rb +2 -0
- data/lib/active_support/isolated_execution_state.rb +72 -0
- data/lib/active_support/json/decoding.rb +27 -26
- data/lib/active_support/json/encoding.rb +16 -6
- data/lib/active_support/json.rb +2 -0
- data/lib/active_support/key_generator.rb +25 -38
- data/lib/active_support/lazy_load_hooks.rb +35 -6
- data/lib/active_support/locale/en.rb +33 -0
- data/lib/active_support/locale/en.yml +8 -4
- data/lib/active_support/log_subscriber/test_helper.rb +4 -2
- data/lib/active_support/log_subscriber.rb +54 -13
- data/lib/active_support/logger.rb +4 -17
- data/lib/active_support/logger_silence.rb +13 -20
- data/lib/active_support/logger_thread_safe_level.rb +48 -10
- data/lib/active_support/message_encryptor.rb +111 -37
- data/lib/active_support/message_verifier.rb +124 -21
- data/lib/active_support/messages/metadata.rb +80 -0
- data/lib/active_support/messages/rotation_configuration.rb +23 -0
- data/lib/active_support/messages/rotator.rb +57 -0
- data/lib/active_support/multibyte/chars.rb +19 -76
- data/lib/active_support/multibyte/unicode.rb +9 -331
- data/lib/active_support/multibyte.rb +3 -1
- data/lib/active_support/notifications/fanout.rb +165 -37
- data/lib/active_support/notifications/instrumenter.rb +92 -11
- data/lib/active_support/notifications.rb +96 -30
- data/lib/active_support/number_helper/number_converter.rb +8 -9
- data/lib/active_support/number_helper/number_to_currency_converter.rb +14 -12
- data/lib/active_support/number_helper/number_to_delimited_converter.rb +6 -3
- data/lib/active_support/number_helper/number_to_human_converter.rb +6 -3
- data/lib/active_support/number_helper/number_to_human_size_converter.rb +7 -4
- data/lib/active_support/number_helper/number_to_percentage_converter.rb +5 -1
- data/lib/active_support/number_helper/number_to_phone_converter.rb +6 -3
- data/lib/active_support/number_helper/number_to_rounded_converter.rb +14 -27
- data/lib/active_support/number_helper/rounding_helper.rb +16 -34
- data/lib/active_support/number_helper.rb +38 -12
- data/lib/active_support/option_merger.rb +19 -6
- data/lib/active_support/ordered_hash.rb +4 -2
- data/lib/active_support/ordered_options.rb +18 -6
- data/lib/active_support/parameter_filter.rb +138 -0
- data/lib/active_support/per_thread_registry.rb +8 -1
- data/lib/active_support/proxy_object.rb +2 -0
- data/lib/active_support/rails.rb +3 -10
- data/lib/active_support/railtie.rb +112 -11
- data/lib/active_support/reloader.rb +12 -11
- data/lib/active_support/rescuable.rb +19 -18
- data/lib/active_support/ruby_features.rb +7 -0
- data/lib/active_support/secure_compare_rotator.rb +51 -0
- data/lib/active_support/security_utils.rb +26 -15
- data/lib/active_support/string_inquirer.rb +4 -3
- data/lib/active_support/subscriber.rb +81 -42
- data/lib/active_support/tagged_logging.rb +45 -9
- data/lib/active_support/test_case.rb +86 -2
- data/lib/active_support/testing/assertions.rb +89 -21
- data/lib/active_support/testing/autorun.rb +2 -0
- data/lib/active_support/testing/constant_lookup.rb +2 -0
- data/lib/active_support/testing/declarative.rb +2 -0
- data/lib/active_support/testing/deprecation.rb +54 -2
- data/lib/active_support/testing/file_fixtures.rb +4 -0
- data/lib/active_support/testing/isolation.rb +6 -4
- data/lib/active_support/testing/method_call_assertions.rb +34 -5
- data/lib/active_support/testing/parallelization/server.rb +82 -0
- data/lib/active_support/testing/parallelization/worker.rb +103 -0
- data/lib/active_support/testing/parallelization.rb +55 -0
- data/lib/active_support/testing/parallelize_executor.rb +76 -0
- data/lib/active_support/testing/setup_and_teardown.rb +12 -7
- data/lib/active_support/testing/stream.rb +6 -7
- data/lib/active_support/testing/tagged_logging.rb +3 -1
- data/lib/active_support/testing/time_helpers.rb +91 -15
- data/lib/active_support/time.rb +2 -0
- data/lib/active_support/time_with_zone.rb +168 -56
- data/lib/active_support/values/time_zone.rb +85 -37
- data/lib/active_support/version.rb +3 -1
- data/lib/active_support/xml_mini/jdom.rb +6 -5
- data/lib/active_support/xml_mini/libxml.rb +9 -7
- data/lib/active_support/xml_mini/libxmlsax.rb +7 -5
- data/lib/active_support/xml_mini/nokogiri.rb +8 -6
- data/lib/active_support/xml_mini/nokogirisax.rb +6 -4
- data/lib/active_support/xml_mini/rexml.rb +13 -4
- data/lib/active_support/xml_mini.rb +10 -15
- data/lib/active_support.rb +30 -9
- metadata +76 -35
- data/lib/active_support/core_ext/array/prepend_and_append.rb +0 -7
- data/lib/active_support/core_ext/hash/compact.rb +0 -27
- data/lib/active_support/core_ext/hash/transform_values.rb +0 -30
- data/lib/active_support/core_ext/kernel/agnostics.rb +0 -11
- data/lib/active_support/core_ext/marshal.rb +0 -22
- data/lib/active_support/core_ext/module/reachable.rb +0 -8
- data/lib/active_support/core_ext/numeric/inquiry.rb +0 -26
- data/lib/active_support/core_ext/range/include_range.rb +0 -23
- data/lib/active_support/values/unicode_tables.dat +0 -0
@@ -1,31 +1,41 @@
|
|
1
|
-
|
2
|
-
RANGE_FORMATS = {
|
3
|
-
db: Proc.new { |start, stop| "BETWEEN '#{start.to_s(:db)}' AND '#{stop.to_s(:db)}'" }
|
4
|
-
}
|
1
|
+
# frozen_string_literal: true
|
5
2
|
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
3
|
+
module ActiveSupport
|
4
|
+
module RangeWithFormat
|
5
|
+
RANGE_FORMATS = {
|
6
|
+
db: -> (start, stop) do
|
7
|
+
case start
|
8
|
+
when String then "BETWEEN '#{start}' AND '#{stop}'"
|
9
|
+
else
|
10
|
+
"BETWEEN '#{start.to_fs(:db)}' AND '#{stop.to_fs(:db)}'"
|
11
|
+
end
|
12
|
+
end
|
13
|
+
}
|
14
|
+
|
15
|
+
# Convert range to a formatted string. See RANGE_FORMATS for predefined formats.
|
16
|
+
#
|
17
|
+
# This method is aliased to <tt>to_formatted_s</tt>.
|
18
|
+
#
|
19
|
+
# range = (1..100) # => 1..100
|
20
|
+
#
|
21
|
+
# range.to_s # => "1..100"
|
22
|
+
# range.to_fs(:db) # => "BETWEEN '1' AND '100'"
|
23
|
+
#
|
24
|
+
# == Adding your own range formats to to_s
|
25
|
+
# You can add your own formats to the Range::RANGE_FORMATS hash.
|
26
|
+
# Use the format name as the hash key and a Proc instance.
|
27
|
+
#
|
28
|
+
# # config/initializers/range_formats.rb
|
29
|
+
# Range::RANGE_FORMATS[:short] = ->(start, stop) { "Between #{start.to_fs(:db)} and #{stop.to_fs(:db)}" }
|
30
|
+
def to_fs(format = :default)
|
31
|
+
if formatter = RANGE_FORMATS[format]
|
32
|
+
formatter.call(first, last)
|
33
|
+
else
|
34
|
+
to_s
|
35
|
+
end
|
24
36
|
end
|
37
|
+
alias_method :to_formatted_s, :to_fs
|
25
38
|
end
|
26
|
-
|
27
|
-
alias_method :to_default_s, :to_s
|
28
|
-
alias_method :to_formatted_s, :to_s
|
29
39
|
end
|
30
40
|
|
31
41
|
Range.prepend(ActiveSupport::RangeWithFormat)
|
@@ -0,0 +1,26 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module ActiveSupport
|
4
|
+
module DeprecatedRangeWithFormat # :nodoc:
|
5
|
+
NOT_SET = Object.new # :nodoc:
|
6
|
+
def to_s(format = NOT_SET)
|
7
|
+
if formatter = RangeWithFormat::RANGE_FORMATS[format]
|
8
|
+
ActiveSupport::Deprecation.warn(
|
9
|
+
"Range#to_s(#{format.inspect}) is deprecated. Please use Range#to_fs(#{format.inspect}) instead."
|
10
|
+
)
|
11
|
+
formatter.call(first, last)
|
12
|
+
elsif format == NOT_SET
|
13
|
+
super()
|
14
|
+
else
|
15
|
+
ActiveSupport::Deprecation.warn(
|
16
|
+
"Range#to_s(#{format.inspect}) is deprecated. Please use Range#to_fs(#{format.inspect}) instead."
|
17
|
+
)
|
18
|
+
super()
|
19
|
+
end
|
20
|
+
end
|
21
|
+
alias_method :to_default_s, :to_s
|
22
|
+
deprecate :to_default_s
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
Range.prepend(ActiveSupport::DeprecatedRangeWithFormat)
|
@@ -1,5 +1,9 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "active_support/time_with_zone"
|
4
|
+
|
1
5
|
module ActiveSupport
|
2
|
-
module EachTimeWithZone
|
6
|
+
module EachTimeWithZone # :nodoc:
|
3
7
|
def each(&block)
|
4
8
|
ensure_iteration_allowed
|
5
9
|
super
|
@@ -11,9 +15,8 @@ module ActiveSupport
|
|
11
15
|
end
|
12
16
|
|
13
17
|
private
|
14
|
-
|
15
18
|
def ensure_iteration_allowed
|
16
|
-
raise TypeError, "can't iterate from #{first.class}" if first.is_a?(
|
19
|
+
raise TypeError, "can't iterate from #{first.class}" if first.is_a?(TimeWithZone)
|
17
20
|
end
|
18
21
|
end
|
19
22
|
end
|
@@ -1,8 +1,10 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
class Range
|
2
4
|
# Compare two ranges and see if they overlap each other
|
3
5
|
# (1..5).overlaps?(4..6) # => true
|
4
6
|
# (1..5).overlaps?(7..9) # => false
|
5
7
|
def overlaps?(other)
|
6
|
-
cover?(other.
|
8
|
+
other.begin == self.begin || cover?(other.begin) || other.cover?(self.begin)
|
7
9
|
end
|
8
10
|
end
|
@@ -1,4 +1,7 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
require "active_support/core_ext/range/conversions"
|
2
|
-
require "active_support/core_ext/range/
|
4
|
+
require "active_support/core_ext/range/deprecated_conversions" unless ENV["RAILS_DISABLE_DEPRECATED_TO_S_CONVERSION"]
|
5
|
+
require "active_support/core_ext/range/compare_range"
|
3
6
|
require "active_support/core_ext/range/overlaps"
|
4
7
|
require "active_support/core_ext/range/each"
|
@@ -1,9 +1,14 @@
|
|
1
|
-
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
class Regexp
|
4
|
+
# Returns +true+ if the regexp has the multiline flag set.
|
5
|
+
#
|
6
|
+
# (/./).multiline? # => false
|
7
|
+
# (/./m).multiline? # => true
|
8
|
+
#
|
9
|
+
# Regexp.new(".").multiline? # => false
|
10
|
+
# Regexp.new(".", Regexp::MULTILINE).multiline? # => true
|
2
11
|
def multiline?
|
3
12
|
options & MULTILINE == MULTILINE
|
4
13
|
end
|
5
|
-
|
6
|
-
def match?(string, pos = 0)
|
7
|
-
!!match(string, pos)
|
8
|
-
end unless //.respond_to?(:match?)
|
9
14
|
end
|
@@ -1,18 +1,21 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
require "securerandom"
|
2
4
|
|
3
5
|
module SecureRandom
|
4
6
|
BASE58_ALPHABET = ("0".."9").to_a + ("A".."Z").to_a + ("a".."z").to_a - ["0", "O", "I", "l"]
|
7
|
+
BASE36_ALPHABET = ("0".."9").to_a + ("a".."z").to_a
|
8
|
+
|
5
9
|
# SecureRandom.base58 generates a random base58 string.
|
6
10
|
#
|
7
|
-
# The argument _n_ specifies the length
|
11
|
+
# The argument _n_ specifies the length of the random string to be generated.
|
8
12
|
#
|
9
13
|
# If _n_ is not specified or is +nil+, 16 is assumed. It may be larger in the future.
|
10
14
|
#
|
11
|
-
# The result may contain alphanumeric characters except 0, O, I and l
|
15
|
+
# The result may contain alphanumeric characters except 0, O, I, and l.
|
12
16
|
#
|
13
17
|
# p SecureRandom.base58 # => "4kUgL2pdQMSCQtjE"
|
14
18
|
# p SecureRandom.base58(24) # => "77TMHrHJFvFDwodq8w7Ev2m7"
|
15
|
-
#
|
16
19
|
def self.base58(n = 16)
|
17
20
|
SecureRandom.random_bytes(n).unpack("C*").map do |byte|
|
18
21
|
idx = byte % 64
|
@@ -20,4 +23,23 @@ module SecureRandom
|
|
20
23
|
BASE58_ALPHABET[idx]
|
21
24
|
end.join
|
22
25
|
end
|
26
|
+
|
27
|
+
# SecureRandom.base36 generates a random base36 string in lowercase.
|
28
|
+
#
|
29
|
+
# The argument _n_ specifies the length of the random string to be generated.
|
30
|
+
#
|
31
|
+
# If _n_ is not specified or is +nil+, 16 is assumed. It may be larger in the future.
|
32
|
+
# This method can be used over +base58+ if a deterministic case key is necessary.
|
33
|
+
#
|
34
|
+
# The result will contain alphanumeric characters in lowercase.
|
35
|
+
#
|
36
|
+
# p SecureRandom.base36 # => "4kugl2pdqmscqtje"
|
37
|
+
# p SecureRandom.base36(24) # => "77tmhrhjfvfdwodq8w7ev2m7"
|
38
|
+
def self.base36(n = 16)
|
39
|
+
SecureRandom.random_bytes(n).unpack("C*").map do |byte|
|
40
|
+
idx = byte % 64
|
41
|
+
idx = SecureRandom.random_number(36) if idx >= 36
|
42
|
+
BASE36_ALPHABET[idx]
|
43
|
+
end.join
|
44
|
+
end
|
23
45
|
end
|
@@ -1,3 +1,5 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
class String
|
2
4
|
# If you pass a single integer, returns a substring of one character at that
|
3
5
|
# position. The first character of the string is at position 0, the next at
|
@@ -42,7 +44,7 @@ class String
|
|
42
44
|
# str.from(0).to(-1) # => "hello"
|
43
45
|
# str.from(1).to(-2) # => "ell"
|
44
46
|
def from(position)
|
45
|
-
self[position
|
47
|
+
self[position, length]
|
46
48
|
end
|
47
49
|
|
48
50
|
# Returns a substring from the beginning of the string to the given position.
|
@@ -59,7 +61,8 @@ class String
|
|
59
61
|
# str.from(0).to(-1) # => "hello"
|
60
62
|
# str.from(1).to(-2) # => "ell"
|
61
63
|
def to(position)
|
62
|
-
|
64
|
+
position += size if position < 0
|
65
|
+
self[0, position + 1] || +""
|
63
66
|
end
|
64
67
|
|
65
68
|
# Returns the first character. If a limit is supplied, returns a substring
|
@@ -73,13 +76,7 @@ class String
|
|
73
76
|
# str.first(0) # => ""
|
74
77
|
# str.first(6) # => "hello"
|
75
78
|
def first(limit = 1)
|
76
|
-
|
77
|
-
""
|
78
|
-
elsif limit >= size
|
79
|
-
dup
|
80
|
-
else
|
81
|
-
to(limit - 1)
|
82
|
-
end
|
79
|
+
self[0, limit] || raise(ArgumentError, "negative limit")
|
83
80
|
end
|
84
81
|
|
85
82
|
# Returns the last character of the string. If a limit is supplied, returns a substring
|
@@ -93,12 +90,6 @@ class String
|
|
93
90
|
# str.last(0) # => ""
|
94
91
|
# str.last(6) # => "hello"
|
95
92
|
def last(limit = 1)
|
96
|
-
|
97
|
-
""
|
98
|
-
elsif limit >= size
|
99
|
-
dup
|
100
|
-
else
|
101
|
-
from(-limit)
|
102
|
-
end
|
93
|
+
self[[length - limit, 0].max, limit] || raise(ArgumentError, "negative limit")
|
103
94
|
end
|
104
95
|
end
|
@@ -1,12 +1,14 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
require "date"
|
2
4
|
require "active_support/core_ext/time/calculations"
|
3
5
|
|
4
6
|
class String
|
5
7
|
# Converts a string to a Time value.
|
6
|
-
# The +form+ can be either
|
8
|
+
# The +form+ can be either +:utc+ or +:local+ (default +:local+).
|
7
9
|
#
|
8
10
|
# The time is parsed using Time.parse method.
|
9
|
-
# If +form+ is
|
11
|
+
# If +form+ is +:local+, then the time is in the system timezone.
|
10
12
|
# If the date part is missing then the current date is used and if
|
11
13
|
# the time part is missing then it is assumed to be 00:00:00.
|
12
14
|
#
|
@@ -16,6 +18,7 @@ class String
|
|
16
18
|
# "2012-12-13T06:12".to_time # => 2012-12-13 06:12:00 +0100
|
17
19
|
# "2012-12-13T06:12".to_time(:utc) # => 2012-12-13 06:12:00 UTC
|
18
20
|
# "12/13/2012".to_time # => ArgumentError: argument out of range
|
21
|
+
# "1604326192".to_time # => ArgumentError: argument out of range
|
19
22
|
def to_time(form = :local)
|
20
23
|
parts = Date._parse(self, false)
|
21
24
|
used_keys = %i(year mon mday hour min sec sec_fraction offset)
|
@@ -1,3 +1,5 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
class String
|
2
4
|
# Returns the string, first removing all whitespace on both ends of
|
3
5
|
# the string, and then changing remaining consecutive whitespace
|
@@ -73,7 +75,48 @@ class String
|
|
73
75
|
length_with_room_for_omission
|
74
76
|
end
|
75
77
|
|
76
|
-
"#{self[0, stop]}#{omission}"
|
78
|
+
+"#{self[0, stop]}#{omission}"
|
79
|
+
end
|
80
|
+
|
81
|
+
# Truncates +text+ to at most <tt>bytesize</tt> bytes in length without
|
82
|
+
# breaking string encoding by splitting multibyte characters or breaking
|
83
|
+
# grapheme clusters ("perceptual characters") by truncating at combining
|
84
|
+
# characters.
|
85
|
+
#
|
86
|
+
# >> "🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪".size
|
87
|
+
# => 20
|
88
|
+
# >> "🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪".bytesize
|
89
|
+
# => 80
|
90
|
+
# >> "🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪🔪".truncate_bytes(20)
|
91
|
+
# => "🔪🔪🔪🔪…"
|
92
|
+
#
|
93
|
+
# The truncated text ends with the <tt>:omission</tt> string, defaulting
|
94
|
+
# to "…", for a total length not exceeding <tt>bytesize</tt>.
|
95
|
+
def truncate_bytes(truncate_at, omission: "…")
|
96
|
+
omission ||= ""
|
97
|
+
|
98
|
+
case
|
99
|
+
when bytesize <= truncate_at
|
100
|
+
dup
|
101
|
+
when omission.bytesize > truncate_at
|
102
|
+
raise ArgumentError, "Omission #{omission.inspect} is #{omission.bytesize}, larger than the truncation length of #{truncate_at} bytes"
|
103
|
+
when omission.bytesize == truncate_at
|
104
|
+
omission.dup
|
105
|
+
else
|
106
|
+
self.class.new.tap do |cut|
|
107
|
+
cut_at = truncate_at - omission.bytesize
|
108
|
+
|
109
|
+
each_grapheme_cluster do |grapheme|
|
110
|
+
if cut.bytesize + grapheme.bytesize <= cut_at
|
111
|
+
cut << grapheme
|
112
|
+
else
|
113
|
+
break
|
114
|
+
end
|
115
|
+
end
|
116
|
+
|
117
|
+
cut << omission
|
118
|
+
end
|
119
|
+
end
|
77
120
|
end
|
78
121
|
|
79
122
|
# Truncates a given +text+ after a given number of words (<tt>words_count</tt>):
|
@@ -1,3 +1,5 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
require "active_support/inflector/methods"
|
2
4
|
require "active_support/inflector/transliterate"
|
3
5
|
|
@@ -28,6 +30,8 @@ class String
|
|
28
30
|
# 'apple'.pluralize(2) # => "apples"
|
29
31
|
# 'ley'.pluralize(:es) # => "leyes"
|
30
32
|
# 'ley'.pluralize(1, :es) # => "ley"
|
33
|
+
#
|
34
|
+
# See ActiveSupport::Inflector.pluralize.
|
31
35
|
def pluralize(count = nil, locale = :en)
|
32
36
|
locale = count if count.is_a?(Symbol)
|
33
37
|
if count == 1
|
@@ -51,28 +55,34 @@ class String
|
|
51
55
|
# 'the blue mailmen'.singularize # => "the blue mailman"
|
52
56
|
# 'CamelOctopi'.singularize # => "CamelOctopus"
|
53
57
|
# 'leyes'.singularize(:es) # => "ley"
|
58
|
+
#
|
59
|
+
# See ActiveSupport::Inflector.singularize.
|
54
60
|
def singularize(locale = :en)
|
55
61
|
ActiveSupport::Inflector.singularize(self, locale)
|
56
62
|
end
|
57
63
|
|
58
64
|
# +constantize+ tries to find a declared constant with the name specified
|
59
65
|
# in the string. It raises a NameError when the name is not in CamelCase
|
60
|
-
# or is not initialized.
|
66
|
+
# or is not initialized.
|
61
67
|
#
|
62
68
|
# 'Module'.constantize # => Module
|
63
69
|
# 'Class'.constantize # => Class
|
64
70
|
# 'blargle'.constantize # => NameError: wrong constant name blargle
|
71
|
+
#
|
72
|
+
# See ActiveSupport::Inflector.constantize.
|
65
73
|
def constantize
|
66
74
|
ActiveSupport::Inflector.constantize(self)
|
67
75
|
end
|
68
76
|
|
69
77
|
# +safe_constantize+ tries to find a declared constant with the name specified
|
70
78
|
# in the string. It returns +nil+ when the name is not in CamelCase
|
71
|
-
# or is not initialized.
|
79
|
+
# or is not initialized.
|
72
80
|
#
|
73
81
|
# 'Module'.safe_constantize # => Module
|
74
82
|
# 'Class'.safe_constantize # => Class
|
75
83
|
# 'blargle'.safe_constantize # => nil
|
84
|
+
#
|
85
|
+
# See ActiveSupport::Inflector.safe_constantize.
|
76
86
|
def safe_constantize
|
77
87
|
ActiveSupport::Inflector.safe_constantize(self)
|
78
88
|
end
|
@@ -86,12 +96,18 @@ class String
|
|
86
96
|
# 'active_record'.camelize(:lower) # => "activeRecord"
|
87
97
|
# 'active_record/errors'.camelize # => "ActiveRecord::Errors"
|
88
98
|
# 'active_record/errors'.camelize(:lower) # => "activeRecord::Errors"
|
99
|
+
#
|
100
|
+
# +camelize+ is also aliased as +camelcase+.
|
101
|
+
#
|
102
|
+
# See ActiveSupport::Inflector.camelize.
|
89
103
|
def camelize(first_letter = :upper)
|
90
104
|
case first_letter
|
91
105
|
when :upper
|
92
106
|
ActiveSupport::Inflector.camelize(self, true)
|
93
107
|
when :lower
|
94
108
|
ActiveSupport::Inflector.camelize(self, false)
|
109
|
+
else
|
110
|
+
raise ArgumentError, "Invalid option, use either :upper or :lower."
|
95
111
|
end
|
96
112
|
end
|
97
113
|
alias_method :camelcase, :camelize
|
@@ -100,12 +116,19 @@ class String
|
|
100
116
|
# a nicer looking title. +titleize+ is meant for creating pretty output. It is not
|
101
117
|
# used in the Rails internals.
|
102
118
|
#
|
119
|
+
# The trailing '_id','Id'.. can be kept and capitalized by setting the
|
120
|
+
# optional parameter +keep_id_suffix+ to true.
|
121
|
+
# By default, this parameter is false.
|
122
|
+
#
|
123
|
+
# 'man from the boondocks'.titleize # => "Man From The Boondocks"
|
124
|
+
# 'x-men: the last stand'.titleize # => "X Men: The Last Stand"
|
125
|
+
# 'string_ending_with_id'.titleize(keep_id_suffix: true) # => "String Ending With Id"
|
126
|
+
#
|
103
127
|
# +titleize+ is also aliased as +titlecase+.
|
104
128
|
#
|
105
|
-
#
|
106
|
-
|
107
|
-
|
108
|
-
ActiveSupport::Inflector.titleize(self)
|
129
|
+
# See ActiveSupport::Inflector.titleize.
|
130
|
+
def titleize(keep_id_suffix: false)
|
131
|
+
ActiveSupport::Inflector.titleize(self, keep_id_suffix: keep_id_suffix)
|
109
132
|
end
|
110
133
|
alias_method :titlecase, :titleize
|
111
134
|
|
@@ -115,6 +138,8 @@ class String
|
|
115
138
|
#
|
116
139
|
# 'ActiveModel'.underscore # => "active_model"
|
117
140
|
# 'ActiveModel::Errors'.underscore # => "active_model/errors"
|
141
|
+
#
|
142
|
+
# See ActiveSupport::Inflector.underscore.
|
118
143
|
def underscore
|
119
144
|
ActiveSupport::Inflector.underscore(self)
|
120
145
|
end
|
@@ -122,6 +147,8 @@ class String
|
|
122
147
|
# Replaces underscores with dashes in the string.
|
123
148
|
#
|
124
149
|
# 'puni_puni'.dasherize # => "puni-puni"
|
150
|
+
#
|
151
|
+
# See ActiveSupport::Inflector.dasherize.
|
125
152
|
def dasherize
|
126
153
|
ActiveSupport::Inflector.dasherize(self)
|
127
154
|
end
|
@@ -133,6 +160,8 @@ class String
|
|
133
160
|
# '::Inflections'.demodulize # => "Inflections"
|
134
161
|
# ''.demodulize # => ''
|
135
162
|
#
|
163
|
+
# See ActiveSupport::Inflector.demodulize.
|
164
|
+
#
|
136
165
|
# See also +deconstantize+.
|
137
166
|
def demodulize
|
138
167
|
ActiveSupport::Inflector.demodulize(self)
|
@@ -146,6 +175,8 @@ class String
|
|
146
175
|
# '::String'.deconstantize # => ""
|
147
176
|
# ''.deconstantize # => ""
|
148
177
|
#
|
178
|
+
# See ActiveSupport::Inflector.deconstantize.
|
179
|
+
#
|
149
180
|
# See also +demodulize+.
|
150
181
|
def deconstantize
|
151
182
|
ActiveSupport::Inflector.deconstantize(self)
|
@@ -153,6 +184,11 @@ class String
|
|
153
184
|
|
154
185
|
# Replaces special characters in a string so that it may be used as part of a 'pretty' URL.
|
155
186
|
#
|
187
|
+
# If the optional parameter +locale+ is specified,
|
188
|
+
# the word will be parameterized as a word of that language.
|
189
|
+
# By default, this parameter is set to <tt>nil</tt> and it will use
|
190
|
+
# the configured <tt>I18n.locale</tt>.
|
191
|
+
#
|
156
192
|
# class Person
|
157
193
|
# def to_param
|
158
194
|
# "#{id}-#{name.parameterize}"
|
@@ -165,7 +201,7 @@ class String
|
|
165
201
|
# <%= link_to(@person.name, person_path) %>
|
166
202
|
# # => <a href="/person/1-donald-e-knuth">Donald E. Knuth</a>
|
167
203
|
#
|
168
|
-
# To preserve the case of the characters in a string, use the
|
204
|
+
# To preserve the case of the characters in a string, use the +preserve_case+ argument.
|
169
205
|
#
|
170
206
|
# class Person
|
171
207
|
# def to_param
|
@@ -178,8 +214,10 @@ class String
|
|
178
214
|
#
|
179
215
|
# <%= link_to(@person.name, person_path) %>
|
180
216
|
# # => <a href="/person/1-Donald-E-Knuth">Donald E. Knuth</a>
|
181
|
-
|
182
|
-
|
217
|
+
#
|
218
|
+
# See ActiveSupport::Inflector.parameterize.
|
219
|
+
def parameterize(separator: "-", preserve_case: false, locale: nil)
|
220
|
+
ActiveSupport::Inflector.parameterize(self, separator: separator, preserve_case: preserve_case, locale: locale)
|
183
221
|
end
|
184
222
|
|
185
223
|
# Creates the name of a table like Rails does for models to table names. This method
|
@@ -188,6 +226,8 @@ class String
|
|
188
226
|
# 'RawScaledScorer'.tableize # => "raw_scaled_scorers"
|
189
227
|
# 'ham_and_egg'.tableize # => "ham_and_eggs"
|
190
228
|
# 'fancyCategory'.tableize # => "fancy_categories"
|
229
|
+
#
|
230
|
+
# See ActiveSupport::Inflector.tableize.
|
191
231
|
def tableize
|
192
232
|
ActiveSupport::Inflector.tableize(self)
|
193
233
|
end
|
@@ -198,11 +238,13 @@ class String
|
|
198
238
|
#
|
199
239
|
# 'ham_and_eggs'.classify # => "HamAndEgg"
|
200
240
|
# 'posts'.classify # => "Post"
|
241
|
+
#
|
242
|
+
# See ActiveSupport::Inflector.classify.
|
201
243
|
def classify
|
202
244
|
ActiveSupport::Inflector.classify(self)
|
203
245
|
end
|
204
246
|
|
205
|
-
# Capitalizes the first word, turns underscores into spaces, and strips a
|
247
|
+
# Capitalizes the first word, turns underscores into spaces, and (by default)strips a
|
206
248
|
# trailing '_id' if present.
|
207
249
|
# Like +titleize+, this is meant for creating pretty output.
|
208
250
|
#
|
@@ -210,12 +252,19 @@ class String
|
|
210
252
|
# optional parameter +capitalize+ to false.
|
211
253
|
# By default, this parameter is true.
|
212
254
|
#
|
213
|
-
#
|
214
|
-
#
|
215
|
-
#
|
216
|
-
#
|
217
|
-
|
218
|
-
|
255
|
+
# The trailing '_id' can be kept and capitalized by setting the
|
256
|
+
# optional parameter +keep_id_suffix+ to true.
|
257
|
+
# By default, this parameter is false.
|
258
|
+
#
|
259
|
+
# 'employee_salary'.humanize # => "Employee salary"
|
260
|
+
# 'author_id'.humanize # => "Author"
|
261
|
+
# 'author_id'.humanize(capitalize: false) # => "author"
|
262
|
+
# '_id'.humanize # => "Id"
|
263
|
+
# 'author_id'.humanize(keep_id_suffix: true) # => "Author id"
|
264
|
+
#
|
265
|
+
# See ActiveSupport::Inflector.humanize.
|
266
|
+
def humanize(capitalize: true, keep_id_suffix: false)
|
267
|
+
ActiveSupport::Inflector.humanize(self, capitalize: capitalize, keep_id_suffix: keep_id_suffix)
|
219
268
|
end
|
220
269
|
|
221
270
|
# Converts just the first character to uppercase.
|
@@ -223,6 +272,8 @@ class String
|
|
223
272
|
# 'what a Lovely Day'.upcase_first # => "What a Lovely Day"
|
224
273
|
# 'w'.upcase_first # => "W"
|
225
274
|
# ''.upcase_first # => ""
|
275
|
+
#
|
276
|
+
# See ActiveSupport::Inflector.upcase_first.
|
226
277
|
def upcase_first
|
227
278
|
ActiveSupport::Inflector.upcase_first(self)
|
228
279
|
end
|
@@ -234,6 +285,8 @@ class String
|
|
234
285
|
# 'Message'.foreign_key # => "message_id"
|
235
286
|
# 'Message'.foreign_key(false) # => "messageid"
|
236
287
|
# 'Admin::Post'.foreign_key # => "post_id"
|
288
|
+
#
|
289
|
+
# See ActiveSupport::Inflector.foreign_key.
|
237
290
|
def foreign_key(separate_class_name_and_id_with_underscore = true)
|
238
291
|
ActiveSupport::Inflector.foreign_key(self, separate_class_name_and_id_with_underscore)
|
239
292
|
end
|
@@ -1,7 +1,10 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
require "active_support/string_inquirer"
|
4
|
+
require "active_support/environment_inquirer"
|
2
5
|
|
3
6
|
class String
|
4
|
-
# Wraps the current string in the
|
7
|
+
# Wraps the current string in the ActiveSupport::StringInquirer class,
|
5
8
|
# which gives you a prettier way to test for equality.
|
6
9
|
#
|
7
10
|
# env = 'production'.inquiry
|
@@ -1,3 +1,5 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
require "active_support/multibyte"
|
2
4
|
|
3
5
|
class String
|
@@ -9,11 +11,14 @@ class String
|
|
9
11
|
# encapsulates the original string. A Unicode safe version of all the String methods are defined on this proxy
|
10
12
|
# class. If the proxy class doesn't respond to a certain method, it's forwarded to the encapsulated string.
|
11
13
|
#
|
12
|
-
# >> "lj".upcase
|
13
|
-
# => "lj"
|
14
14
|
# >> "lj".mb_chars.upcase.to_s
|
15
15
|
# => "LJ"
|
16
16
|
#
|
17
|
+
# NOTE: Ruby 2.4 and later support native Unicode case mappings:
|
18
|
+
#
|
19
|
+
# >> "lj".upcase
|
20
|
+
# => "LJ"
|
21
|
+
#
|
17
22
|
# == Method chaining
|
18
23
|
#
|
19
24
|
# All the methods on the Chars proxy which normally return a string will return a Chars object. This allows
|
@@ -42,9 +47,9 @@ class String
|
|
42
47
|
# iso_str.is_utf8? # => false
|
43
48
|
def is_utf8?
|
44
49
|
case encoding
|
45
|
-
when Encoding::UTF_8
|
50
|
+
when Encoding::UTF_8, Encoding::US_ASCII
|
46
51
|
valid_encoding?
|
47
|
-
when Encoding::ASCII_8BIT
|
52
|
+
when Encoding::ASCII_8BIT
|
48
53
|
dup.force_encoding(Encoding::UTF_8).valid_encoding?
|
49
54
|
else
|
50
55
|
false
|