rubocop-performance 1.18.0 → 1.19.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/config/default.yml +6 -0
- data/lib/rubocop/cop/performance/array_semi_infinite_range_slice.rb +2 -1
- data/lib/rubocop/cop/performance/delete_prefix.rb +5 -2
- data/lib/rubocop/cop/performance/delete_suffix.rb +5 -2
- data/lib/rubocop/cop/performance/detect.rb +3 -2
- data/lib/rubocop/cop/performance/end_with.rb +4 -2
- data/lib/rubocop/cop/performance/fixed_size.rb +2 -2
- data/lib/rubocop/cop/performance/inefficient_hash_search.rb +15 -9
- data/lib/rubocop/cop/performance/map_compact.rb +3 -2
- data/lib/rubocop/cop/performance/map_method_chain.rb +87 -0
- data/lib/rubocop/cop/performance/redundant_merge.rb +2 -2
- data/lib/rubocop/cop/performance/redundant_split_regexp_argument.rb +2 -1
- data/lib/rubocop/cop/performance/reverse_each.rb +2 -1
- data/lib/rubocop/cop/performance/reverse_first.rb +2 -1
- data/lib/rubocop/cop/performance/select_map.rb +1 -0
- data/lib/rubocop/cop/performance/squeeze.rb +5 -2
- data/lib/rubocop/cop/performance/start_with.rb +4 -2
- data/lib/rubocop/cop/performance/string_include.rb +6 -2
- data/lib/rubocop/cop/performance/string_replacement.rb +2 -1
- data/lib/rubocop/cop/performance/uri_default_parser.rb +1 -1
- data/lib/rubocop/cop/performance_cops.rb +1 -0
- data/lib/rubocop/performance/version.rb +1 -1
- metadata +4 -3
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 06f3e8346dc7f9be72a1f18c62a25dc02aeac41debcfe3c58df68e2a6904df43
|
4
|
+
data.tar.gz: f01facdb92a3056d05990e2ed2b6b1920de0501edf53a08e95e08620651c8557
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 07eb541698b6ccf2985ef62392bd78703bf6607e2877ef3865ab1762d62910c4c346fbb7e9bc48af7b7d98b0e1ad22e8c79ea2425555fbe75c2a5e614837eaa7
|
7
|
+
data.tar.gz: 60fc9f900906cca518d0da62170f71ae6e5f5ffd44f4c1cbe75af83f9a1fef252b6bab95d3af4f49f328d4a856cd17c7f47621ee62575ab282eacfd26dc09841
|
data/config/default.yml
CHANGED
@@ -193,6 +193,12 @@ Performance/MapCompact:
|
|
193
193
|
SafeAutoCorrect: false
|
194
194
|
VersionAdded: '1.11'
|
195
195
|
|
196
|
+
Performance/MapMethodChain:
|
197
|
+
Description: 'Checks if the `map` method is used in a chain.'
|
198
|
+
Enabled: pending
|
199
|
+
Safe: false
|
200
|
+
VersionAdded: '1.19'
|
201
|
+
|
196
202
|
Performance/MethodObjectAsBlock:
|
197
203
|
Description: 'Use block explicitly instead of block-passing a method object.'
|
198
204
|
Reference: 'https://github.com/JuanitoFatas/fast-ruby#normal-way-to-apply-method-vs-method-code'
|
@@ -39,7 +39,7 @@ module RuboCop
|
|
39
39
|
RESTRICT_ON_SEND = SLICE_METHODS
|
40
40
|
|
41
41
|
def_node_matcher :endless_range_slice?, <<~PATTERN
|
42
|
-
(
|
42
|
+
(call $_ $%SLICE_METHODS $#endless_range?)
|
43
43
|
PATTERN
|
44
44
|
|
45
45
|
def_node_matcher :endless_range?, <<~PATTERN
|
@@ -59,6 +59,7 @@ module RuboCop
|
|
59
59
|
end
|
60
60
|
end
|
61
61
|
end
|
62
|
+
alias on_csend on_send
|
62
63
|
|
63
64
|
private
|
64
65
|
|
@@ -64,9 +64,10 @@ module RuboCop
|
|
64
64
|
}.freeze
|
65
65
|
|
66
66
|
def_node_matcher :delete_prefix_candidate?, <<~PATTERN
|
67
|
-
(
|
67
|
+
(call $!nil? ${:gsub :gsub! :sub :sub!} (regexp (str $#literal_at_start?) (regopt)) (str $_))
|
68
68
|
PATTERN
|
69
69
|
|
70
|
+
# rubocop:disable Metrics/AbcSize
|
70
71
|
def on_send(node)
|
71
72
|
return unless (receiver, bad_method, regexp_str, replace_string = delete_prefix_candidate?(node))
|
72
73
|
return unless replace_string.empty?
|
@@ -80,11 +81,13 @@ module RuboCop
|
|
80
81
|
regexp_str = interpret_string_escapes(regexp_str)
|
81
82
|
string_literal = to_string_literal(regexp_str)
|
82
83
|
|
83
|
-
new_code = "#{receiver.source}
|
84
|
+
new_code = "#{receiver.source}#{node.loc.dot.source}#{good_method}(#{string_literal})"
|
84
85
|
|
85
86
|
corrector.replace(node, new_code)
|
86
87
|
end
|
87
88
|
end
|
89
|
+
# rubocop:enable Metrics/AbcSize
|
90
|
+
alias on_csend on_send
|
88
91
|
end
|
89
92
|
end
|
90
93
|
end
|
@@ -64,9 +64,10 @@ module RuboCop
|
|
64
64
|
}.freeze
|
65
65
|
|
66
66
|
def_node_matcher :delete_suffix_candidate?, <<~PATTERN
|
67
|
-
(
|
67
|
+
(call $!nil? ${:gsub :gsub! :sub :sub!} (regexp (str $#literal_at_end?) (regopt)) (str $_))
|
68
68
|
PATTERN
|
69
69
|
|
70
|
+
# rubocop:disable Metrics/AbcSize
|
70
71
|
def on_send(node)
|
71
72
|
return unless (receiver, bad_method, regexp_str, replace_string = delete_suffix_candidate?(node))
|
72
73
|
return unless replace_string.empty?
|
@@ -80,11 +81,13 @@ module RuboCop
|
|
80
81
|
regexp_str = interpret_string_escapes(regexp_str)
|
81
82
|
string_literal = to_string_literal(regexp_str)
|
82
83
|
|
83
|
-
new_code = "#{receiver.source}
|
84
|
+
new_code = "#{receiver.source}#{node.loc.dot.source}#{good_method}(#{string_literal})"
|
84
85
|
|
85
86
|
corrector.replace(node, new_code)
|
86
87
|
end
|
87
88
|
end
|
89
|
+
# rubocop:enable Metrics/AbcSize
|
90
|
+
alias on_csend on_send
|
88
91
|
end
|
89
92
|
end
|
90
93
|
end
|
@@ -40,9 +40,9 @@ module RuboCop
|
|
40
40
|
|
41
41
|
def_node_matcher :detect_candidate?, <<~PATTERN
|
42
42
|
{
|
43
|
-
(send $(block (
|
43
|
+
(send $(block (call _ %CANDIDATE_METHODS) ...) ${:first :last} $...)
|
44
44
|
(send $(block (send _ %CANDIDATE_METHODS) ...) $:[] (int ${0 -1}))
|
45
|
-
(send $(
|
45
|
+
(send $(call _ %CANDIDATE_METHODS ...) ${:first :last} $...)
|
46
46
|
(send $(send _ %CANDIDATE_METHODS ...) $:[] (int ${0 -1}))
|
47
47
|
}
|
48
48
|
PATTERN
|
@@ -63,6 +63,7 @@ module RuboCop
|
|
63
63
|
register_offense(node, receiver, second_method, index)
|
64
64
|
end
|
65
65
|
end
|
66
|
+
alias on_csend on_send
|
66
67
|
|
67
68
|
private
|
68
69
|
|
@@ -54,7 +54,7 @@ module RuboCop
|
|
54
54
|
RESTRICT_ON_SEND = %i[match =~ match?].freeze
|
55
55
|
|
56
56
|
def_node_matcher :redundant_regex?, <<~PATTERN
|
57
|
-
{(
|
57
|
+
{(call $!nil? {:match :=~ :match?} (regexp (str $#literal_at_end?) (regopt)))
|
58
58
|
(send (regexp (str $#literal_at_end?) (regopt)) {:match :match?} $_)
|
59
59
|
(match-with-lvasgn (regexp (str $#literal_at_end?) (regopt)) $_)}
|
60
60
|
PATTERN
|
@@ -66,12 +66,14 @@ module RuboCop
|
|
66
66
|
receiver, regex_str = regex_str, receiver if receiver.is_a?(String)
|
67
67
|
regex_str = drop_end_metacharacter(regex_str)
|
68
68
|
regex_str = interpret_string_escapes(regex_str)
|
69
|
+
dot = node.loc.dot ? node.loc.dot.source : '.'
|
69
70
|
|
70
|
-
new_source = "#{receiver.source}
|
71
|
+
new_source = "#{receiver.source}#{dot}end_with?(#{to_string_literal(regex_str)})"
|
71
72
|
|
72
73
|
corrector.replace(node, new_source)
|
73
74
|
end
|
74
75
|
end
|
76
|
+
alias on_csend on_send
|
75
77
|
alias on_match_with_lvasgn on_send
|
76
78
|
end
|
77
79
|
end
|
@@ -78,13 +78,13 @@ module RuboCop
|
|
78
78
|
end
|
79
79
|
|
80
80
|
def contains_splat?(node)
|
81
|
-
return unless node.array_type?
|
81
|
+
return false unless node.array_type?
|
82
82
|
|
83
83
|
node.each_child_node(:splat).any?
|
84
84
|
end
|
85
85
|
|
86
86
|
def contains_double_splat?(node)
|
87
|
-
return unless node.hash_type?
|
87
|
+
return false unless node.hash_type?
|
88
88
|
|
89
89
|
node.each_child_node(:kwsplat).any?
|
90
90
|
end
|
@@ -45,7 +45,7 @@ module RuboCop
|
|
45
45
|
RESTRICT_ON_SEND = %i[include?].freeze
|
46
46
|
|
47
47
|
def_node_matcher :inefficient_include?, <<~PATTERN
|
48
|
-
(send (
|
48
|
+
(send (call $_ {:keys :values}) :include? _)
|
49
49
|
PATTERN
|
50
50
|
|
51
51
|
def on_send(node)
|
@@ -56,21 +56,23 @@ module RuboCop
|
|
56
56
|
add_offense(node, message: message) do |corrector|
|
57
57
|
# Replace `keys.include?` or `values.include?` with the appropriate
|
58
58
|
# `key?`/`value?` method.
|
59
|
-
corrector.replace(
|
60
|
-
node,
|
61
|
-
"#{autocorrect_hash_expression(node)}.#{autocorrect_method(node)}(#{autocorrect_argument(node)})"
|
62
|
-
)
|
59
|
+
corrector.replace(node, replacement(node))
|
63
60
|
end
|
64
61
|
end
|
65
62
|
end
|
63
|
+
alias on_csend on_send
|
66
64
|
|
67
65
|
private
|
68
66
|
|
69
67
|
def message(node)
|
70
|
-
"Use `##{
|
68
|
+
"Use `##{correct_method(node)}` instead of `##{current_method(node)}.include?`."
|
71
69
|
end
|
72
70
|
|
73
|
-
def
|
71
|
+
def replacement(node)
|
72
|
+
"#{correct_hash_expression(node)}#{correct_dot(node)}#{correct_method(node)}(#{correct_argument(node)})"
|
73
|
+
end
|
74
|
+
|
75
|
+
def correct_method(node)
|
74
76
|
case current_method(node)
|
75
77
|
when :keys then use_long_method ? 'has_key?' : 'key?'
|
76
78
|
when :values then use_long_method ? 'has_value?' : 'value?'
|
@@ -86,13 +88,17 @@ module RuboCop
|
|
86
88
|
preferred_config && preferred_config['EnforcedStyle'] == 'long' && preferred_config['Enabled']
|
87
89
|
end
|
88
90
|
|
89
|
-
def
|
91
|
+
def correct_argument(node)
|
90
92
|
node.arguments.first.source
|
91
93
|
end
|
92
94
|
|
93
|
-
def
|
95
|
+
def correct_hash_expression(node)
|
94
96
|
node.receiver.receiver.source
|
95
97
|
end
|
98
|
+
|
99
|
+
def correct_dot(node)
|
100
|
+
node.receiver.loc.dot.source
|
101
|
+
end
|
96
102
|
end
|
97
103
|
end
|
98
104
|
end
|
@@ -40,12 +40,12 @@ module RuboCop
|
|
40
40
|
def_node_matcher :map_compact, <<~PATTERN
|
41
41
|
{
|
42
42
|
(send
|
43
|
-
$(
|
43
|
+
$(call _ {:map :collect}
|
44
44
|
(block_pass
|
45
45
|
(sym _))) _)
|
46
46
|
(send
|
47
47
|
(block
|
48
|
-
$(
|
48
|
+
$(call _ {:map :collect})
|
49
49
|
(args ...) _) _)
|
50
50
|
}
|
51
51
|
PATTERN
|
@@ -61,6 +61,7 @@ module RuboCop
|
|
61
61
|
remove_compact_method(corrector, map_node, node, node.parent)
|
62
62
|
end
|
63
63
|
end
|
64
|
+
alias on_csend on_send
|
64
65
|
|
65
66
|
private
|
66
67
|
|
@@ -0,0 +1,87 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module RuboCop
|
4
|
+
module Cop
|
5
|
+
module Performance
|
6
|
+
# Checks if the map method is used in a chain.
|
7
|
+
#
|
8
|
+
# Autocorrection is not supported because an appropriate block variable name cannot be determined automatically.
|
9
|
+
#
|
10
|
+
# @safety
|
11
|
+
# This cop is unsafe because false positives occur if the number of times the first method is executed
|
12
|
+
# affects the return value of subsequent methods.
|
13
|
+
#
|
14
|
+
# [source,ruby]
|
15
|
+
# ----
|
16
|
+
# class X
|
17
|
+
# def initialize
|
18
|
+
# @@num = 0
|
19
|
+
# end
|
20
|
+
#
|
21
|
+
# def foo
|
22
|
+
# @@num += 1
|
23
|
+
# self
|
24
|
+
# end
|
25
|
+
#
|
26
|
+
# def bar
|
27
|
+
# @@num * 2
|
28
|
+
# end
|
29
|
+
# end
|
30
|
+
#
|
31
|
+
# [X.new, X.new].map(&:foo).map(&:bar) # => [4, 4]
|
32
|
+
# [X.new, X.new].map { |x| x.foo.bar } # => [2, 4]
|
33
|
+
# ----
|
34
|
+
#
|
35
|
+
# @example
|
36
|
+
#
|
37
|
+
# # bad
|
38
|
+
# array.map(&:foo).map(&:bar)
|
39
|
+
#
|
40
|
+
# # good
|
41
|
+
# array.map { |item| item.foo.bar }
|
42
|
+
#
|
43
|
+
class MapMethodChain < Base
|
44
|
+
include IgnoredNode
|
45
|
+
|
46
|
+
MSG = 'Use `%<method_name>s { |x| x.%<map_args>s }` instead of `%<method_name>s` method chain.'
|
47
|
+
RESTRICT_ON_SEND = %i[map collect].freeze
|
48
|
+
|
49
|
+
def_node_matcher :block_pass_with_symbol_arg?, <<~PATTERN
|
50
|
+
(:block_pass (:sym $_))
|
51
|
+
PATTERN
|
52
|
+
|
53
|
+
def on_send(node)
|
54
|
+
return if part_of_ignored_node?(node)
|
55
|
+
return unless (map_arg = block_pass_with_symbol_arg?(node.first_argument))
|
56
|
+
|
57
|
+
map_args = [map_arg]
|
58
|
+
|
59
|
+
return unless (begin_of_chained_map_method = find_begin_of_chained_map_method(node, map_args))
|
60
|
+
|
61
|
+
range = begin_of_chained_map_method.loc.selector.begin.join(node.source_range.end)
|
62
|
+
message = format(MSG, method_name: begin_of_chained_map_method.method_name, map_args: map_args.join('.'))
|
63
|
+
|
64
|
+
add_offense(range, message: message)
|
65
|
+
|
66
|
+
ignore_node(node)
|
67
|
+
end
|
68
|
+
|
69
|
+
private
|
70
|
+
|
71
|
+
def find_begin_of_chained_map_method(node, map_args)
|
72
|
+
return unless (chained_map_method = node.receiver)
|
73
|
+
return if !chained_map_method.call_type? || !RESTRICT_ON_SEND.include?(chained_map_method.method_name)
|
74
|
+
return unless (map_arg = block_pass_with_symbol_arg?(chained_map_method.first_argument))
|
75
|
+
|
76
|
+
map_args.unshift(map_arg)
|
77
|
+
|
78
|
+
receiver = chained_map_method.receiver
|
79
|
+
|
80
|
+
return chained_map_method unless receiver.call_type? && block_pass_with_symbol_arg?(receiver.first_argument)
|
81
|
+
|
82
|
+
find_begin_of_chained_map_method(chained_map_method, map_args)
|
83
|
+
end
|
84
|
+
end
|
85
|
+
end
|
86
|
+
end
|
87
|
+
end
|
@@ -109,7 +109,7 @@ module RuboCop
|
|
109
109
|
node = parent
|
110
110
|
else
|
111
111
|
padding = "\n#{leading_spaces(node)}"
|
112
|
-
new_source.gsub!(
|
112
|
+
new_source.gsub!("\n", padding)
|
113
113
|
end
|
114
114
|
|
115
115
|
corrector.replace(node, new_source)
|
@@ -132,7 +132,7 @@ module RuboCop
|
|
132
132
|
def rewrite_with_modifier(node, parent, new_source)
|
133
133
|
indent = ' ' * configured_indentation_width
|
134
134
|
padding = "\n#{indent + leading_spaces(node)}"
|
135
|
-
new_source.gsub!(
|
135
|
+
new_source.gsub!("\n", padding)
|
136
136
|
|
137
137
|
format(WITH_MODIFIER_CORRECTION, keyword: parent.loc.keyword.source,
|
138
138
|
condition: parent.condition.source,
|
@@ -21,7 +21,7 @@ module RuboCop
|
|
21
21
|
STR_SPECIAL_CHARS = %w[\n \" \' \\\\ \t \b \f \r].freeze
|
22
22
|
|
23
23
|
def_node_matcher :split_call_with_regexp?, <<~PATTERN
|
24
|
-
{(
|
24
|
+
{(call !nil? :split $regexp)}
|
25
25
|
PATTERN
|
26
26
|
|
27
27
|
def on_send(node)
|
@@ -35,6 +35,7 @@ module RuboCop
|
|
35
35
|
corrector.replace(regexp_node, "\"#{new_argument}\"")
|
36
36
|
end
|
37
37
|
end
|
38
|
+
alias on_csend on_send
|
38
39
|
|
39
40
|
private
|
40
41
|
|
@@ -27,7 +27,7 @@ module RuboCop
|
|
27
27
|
RESTRICT_ON_SEND = %i[each].freeze
|
28
28
|
|
29
29
|
def_node_matcher :reverse_each?, <<~MATCHER
|
30
|
-
(send (
|
30
|
+
(send (call _ :reverse) :each)
|
31
31
|
MATCHER
|
32
32
|
|
33
33
|
def on_send(node)
|
@@ -41,6 +41,7 @@ module RuboCop
|
|
41
41
|
end
|
42
42
|
end
|
43
43
|
end
|
44
|
+
alias on_csend on_send
|
44
45
|
|
45
46
|
private
|
46
47
|
|
@@ -24,7 +24,7 @@ module RuboCop
|
|
24
24
|
RESTRICT_ON_SEND = %i[first].freeze
|
25
25
|
|
26
26
|
def_node_matcher :reverse_first_candidate?, <<~PATTERN
|
27
|
-
(send $(
|
27
|
+
(send $(call _ :reverse) :first (int _)?)
|
28
28
|
PATTERN
|
29
29
|
|
30
30
|
def on_send(node)
|
@@ -39,6 +39,7 @@ module RuboCop
|
|
39
39
|
end
|
40
40
|
end
|
41
41
|
end
|
42
|
+
alias on_csend on_send
|
42
43
|
|
43
44
|
private
|
44
45
|
|
@@ -27,7 +27,7 @@ module RuboCop
|
|
27
27
|
PREFERRED_METHODS = { gsub: :squeeze, gsub!: :squeeze! }.freeze
|
28
28
|
|
29
29
|
def_node_matcher :squeeze_candidate?, <<~PATTERN
|
30
|
-
(
|
30
|
+
(call
|
31
31
|
$!nil? ${:gsub :gsub!}
|
32
32
|
(regexp
|
33
33
|
(str $#repeating_literal?)
|
@@ -35,6 +35,7 @@ module RuboCop
|
|
35
35
|
(str $_))
|
36
36
|
PATTERN
|
37
37
|
|
38
|
+
# rubocop:disable Metrics/AbcSize
|
38
39
|
def on_send(node)
|
39
40
|
squeeze_candidate?(node) do |receiver, bad_method, regexp_str, replace_str|
|
40
41
|
regexp_str = regexp_str[0..-2] # delete '+' from the end
|
@@ -46,12 +47,14 @@ module RuboCop
|
|
46
47
|
|
47
48
|
add_offense(node.loc.selector, message: message) do |corrector|
|
48
49
|
string_literal = to_string_literal(replace_str)
|
49
|
-
new_code = "#{receiver.source}
|
50
|
+
new_code = "#{receiver.source}#{node.loc.dot.source}#{good_method}(#{string_literal})"
|
50
51
|
|
51
52
|
corrector.replace(node, new_code)
|
52
53
|
end
|
53
54
|
end
|
54
55
|
end
|
56
|
+
# rubocop:enable Metrics/AbcSize
|
57
|
+
alias on_csend on_send
|
55
58
|
|
56
59
|
private
|
57
60
|
|
@@ -54,7 +54,7 @@ module RuboCop
|
|
54
54
|
RESTRICT_ON_SEND = %i[match =~ match?].freeze
|
55
55
|
|
56
56
|
def_node_matcher :redundant_regex?, <<~PATTERN
|
57
|
-
{(
|
57
|
+
{(call $!nil? {:match :=~ :match?} (regexp (str $#literal_at_start?) (regopt)))
|
58
58
|
(send (regexp (str $#literal_at_start?) (regopt)) {:match :match?} $_)
|
59
59
|
(match-with-lvasgn (regexp (str $#literal_at_start?) (regopt)) $_)}
|
60
60
|
PATTERN
|
@@ -66,12 +66,14 @@ module RuboCop
|
|
66
66
|
receiver, regex_str = regex_str, receiver if receiver.is_a?(String)
|
67
67
|
regex_str = drop_start_metacharacter(regex_str)
|
68
68
|
regex_str = interpret_string_escapes(regex_str)
|
69
|
+
dot = node.loc.dot ? node.loc.dot.source : '.'
|
69
70
|
|
70
|
-
new_source = "#{receiver.source}
|
71
|
+
new_source = "#{receiver.source}#{dot}start_with?(#{to_string_literal(regex_str)})"
|
71
72
|
|
72
73
|
corrector.replace(node, new_source)
|
73
74
|
end
|
74
75
|
end
|
76
|
+
alias on_csend on_send
|
75
77
|
alias on_match_with_lvasgn on_send
|
76
78
|
end
|
77
79
|
end
|
@@ -26,11 +26,12 @@ module RuboCop
|
|
26
26
|
RESTRICT_ON_SEND = %i[match =~ !~ match?].freeze
|
27
27
|
|
28
28
|
def_node_matcher :redundant_regex?, <<~PATTERN
|
29
|
-
{(
|
29
|
+
{(call $!nil? {:match :=~ :!~ :match?} (regexp (str $#literal?) (regopt)))
|
30
30
|
(send (regexp (str $#literal?) (regopt)) {:match :match?} $_)
|
31
31
|
(match-with-lvasgn (regexp (str $#literal?) (regopt)) $_)}
|
32
32
|
PATTERN
|
33
33
|
|
34
|
+
# rubocop:disable Metrics/AbcSize
|
34
35
|
def on_send(node)
|
35
36
|
return unless (receiver, regex_str = redundant_regex?(node))
|
36
37
|
|
@@ -40,12 +41,15 @@ module RuboCop
|
|
40
41
|
add_offense(node, message: message) do |corrector|
|
41
42
|
receiver, regex_str = regex_str, receiver if receiver.is_a?(String)
|
42
43
|
regex_str = interpret_string_escapes(regex_str)
|
44
|
+
dot = node.loc.dot ? node.loc.dot.source : '.'
|
43
45
|
|
44
|
-
new_source = "#{'!' if negation}#{receiver.source}
|
46
|
+
new_source = "#{'!' if negation}#{receiver.source}#{dot}include?(#{to_string_literal(regex_str)})"
|
45
47
|
|
46
48
|
corrector.replace(node, new_source)
|
47
49
|
end
|
48
50
|
end
|
51
|
+
# rubocop:enable Metrics/AbcSize
|
52
|
+
alias on_csend on_send
|
49
53
|
alias on_match_with_lvasgn on_send
|
50
54
|
|
51
55
|
private
|
@@ -29,7 +29,7 @@ module RuboCop
|
|
29
29
|
BANG = '!'
|
30
30
|
|
31
31
|
def_node_matcher :string_replacement?, <<~PATTERN
|
32
|
-
(
|
32
|
+
(call _ {:gsub :gsub!}
|
33
33
|
${regexp str (send (const nil? :Regexp) {:new :compile} _)}
|
34
34
|
$str)
|
35
35
|
PATTERN
|
@@ -42,6 +42,7 @@ module RuboCop
|
|
42
42
|
offense(node, first_param, second_param)
|
43
43
|
end
|
44
44
|
end
|
45
|
+
alias on_csend on_send
|
45
46
|
|
46
47
|
private
|
47
48
|
|
@@ -25,6 +25,7 @@ require_relative 'performance/fixed_size'
|
|
25
25
|
require_relative 'performance/flat_map'
|
26
26
|
require_relative 'performance/inefficient_hash_search'
|
27
27
|
require_relative 'performance/map_compact'
|
28
|
+
require_relative 'performance/map_method_chain'
|
28
29
|
require_relative 'performance/method_object_as_block'
|
29
30
|
require_relative 'performance/open_struct'
|
30
31
|
require_relative 'performance/range_include'
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: rubocop-performance
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.
|
4
|
+
version: 1.19.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Bozhidar Batsov
|
@@ -10,7 +10,7 @@ authors:
|
|
10
10
|
autorequire:
|
11
11
|
bindir: bin
|
12
12
|
cert_chain: []
|
13
|
-
date: 2023-
|
13
|
+
date: 2023-08-13 00:00:00.000000000 Z
|
14
14
|
dependencies:
|
15
15
|
- !ruby/object:Gem::Dependency
|
16
16
|
name: rubocop
|
@@ -87,6 +87,7 @@ files:
|
|
87
87
|
- lib/rubocop/cop/performance/inefficient_hash_search.rb
|
88
88
|
- lib/rubocop/cop/performance/io_readlines.rb
|
89
89
|
- lib/rubocop/cop/performance/map_compact.rb
|
90
|
+
- lib/rubocop/cop/performance/map_method_chain.rb
|
90
91
|
- lib/rubocop/cop/performance/method_object_as_block.rb
|
91
92
|
- lib/rubocop/cop/performance/open_struct.rb
|
92
93
|
- lib/rubocop/cop/performance/range_include.rb
|
@@ -123,7 +124,7 @@ metadata:
|
|
123
124
|
homepage_uri: https://docs.rubocop.org/rubocop-performance/
|
124
125
|
changelog_uri: https://github.com/rubocop/rubocop-performance/blob/master/CHANGELOG.md
|
125
126
|
source_code_uri: https://github.com/rubocop/rubocop-performance/
|
126
|
-
documentation_uri: https://docs.rubocop.org/rubocop-performance/1.
|
127
|
+
documentation_uri: https://docs.rubocop.org/rubocop-performance/1.19/
|
127
128
|
bug_tracker_uri: https://github.com/rubocop/rubocop-performance/issues
|
128
129
|
rubygems_mfa_required: 'true'
|
129
130
|
post_install_message:
|