rubocop-performance 1.13.3 → 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.
Files changed (58) hide show
  1. checksums.yaml +4 -4
  2. data/LICENSE.txt +1 -1
  3. data/README.md +2 -2
  4. data/config/default.yml +13 -2
  5. data/lib/rubocop/cop/mixin/regexp_metacharacter.rb +2 -2
  6. data/lib/rubocop/cop/mixin/sort_block.rb +7 -0
  7. data/lib/rubocop/cop/performance/ancestors_include.rb +1 -2
  8. data/lib/rubocop/cop/performance/array_semi_infinite_range_slice.rb +3 -2
  9. data/lib/rubocop/cop/performance/big_decimal_with_numeric_argument.rb +2 -6
  10. data/lib/rubocop/cop/performance/bind_call.rb +1 -2
  11. data/lib/rubocop/cop/performance/block_given_with_explicit_block.rb +1 -1
  12. data/lib/rubocop/cop/performance/caller.rb +1 -2
  13. data/lib/rubocop/cop/performance/case_when_splat.rb +7 -13
  14. data/lib/rubocop/cop/performance/casecmp.rb +10 -12
  15. data/lib/rubocop/cop/performance/chain_array_allocation.rb +5 -5
  16. data/lib/rubocop/cop/performance/collection_literal_in_loop.rb +4 -6
  17. data/lib/rubocop/cop/performance/compare_with_block.rb +20 -11
  18. data/lib/rubocop/cop/performance/concurrent_monotonic_time.rb +1 -1
  19. data/lib/rubocop/cop/performance/constant_regexp.rb +6 -4
  20. data/lib/rubocop/cop/performance/count.rb +39 -3
  21. data/lib/rubocop/cop/performance/delete_prefix.rb +8 -2
  22. data/lib/rubocop/cop/performance/delete_suffix.rb +8 -2
  23. data/lib/rubocop/cop/performance/detect.rb +7 -6
  24. data/lib/rubocop/cop/performance/double_start_end_with.rb +4 -5
  25. data/lib/rubocop/cop/performance/end_with.rb +7 -6
  26. data/lib/rubocop/cop/performance/fixed_size.rb +2 -2
  27. data/lib/rubocop/cop/performance/flat_map.rb +7 -5
  28. data/lib/rubocop/cop/performance/inefficient_hash_search.rb +17 -15
  29. data/lib/rubocop/cop/performance/io_readlines.rb +2 -2
  30. data/lib/rubocop/cop/performance/map_compact.rb +9 -4
  31. data/lib/rubocop/cop/performance/map_method_chain.rb +87 -0
  32. data/lib/rubocop/cop/performance/method_object_as_block.rb +1 -1
  33. data/lib/rubocop/cop/performance/open_struct.rb +2 -3
  34. data/lib/rubocop/cop/performance/range_include.rb +2 -2
  35. data/lib/rubocop/cop/performance/redundant_block_call.rb +2 -2
  36. data/lib/rubocop/cop/performance/redundant_equality_comparison_block.rb +38 -3
  37. data/lib/rubocop/cop/performance/redundant_match.rb +10 -9
  38. data/lib/rubocop/cop/performance/redundant_merge.rb +9 -16
  39. data/lib/rubocop/cop/performance/redundant_sort_block.rb +17 -10
  40. data/lib/rubocop/cop/performance/redundant_split_regexp_argument.rb +3 -2
  41. data/lib/rubocop/cop/performance/redundant_string_chars.rb +10 -6
  42. data/lib/rubocop/cop/performance/regexp_match.rb +23 -24
  43. data/lib/rubocop/cop/performance/reverse_each.rb +3 -3
  44. data/lib/rubocop/cop/performance/reverse_first.rb +4 -3
  45. data/lib/rubocop/cop/performance/select_map.rb +2 -1
  46. data/lib/rubocop/cop/performance/size.rb +1 -2
  47. data/lib/rubocop/cop/performance/sort_reverse.rb +19 -10
  48. data/lib/rubocop/cop/performance/squeeze.rb +8 -8
  49. data/lib/rubocop/cop/performance/start_with.rb +7 -6
  50. data/lib/rubocop/cop/performance/string_identifier_argument.rb +16 -11
  51. data/lib/rubocop/cop/performance/string_include.rb +23 -17
  52. data/lib/rubocop/cop/performance/string_replacement.rb +7 -10
  53. data/lib/rubocop/cop/performance/sum.rb +7 -4
  54. data/lib/rubocop/cop/performance/times_map.rb +6 -7
  55. data/lib/rubocop/cop/performance/uri_default_parser.rb +4 -6
  56. data/lib/rubocop/cop/performance_cops.rb +1 -0
  57. data/lib/rubocop/performance/version.rb +1 -1
  58. metadata +6 -5
@@ -3,47 +3,53 @@
3
3
  module RuboCop
4
4
  module Cop
5
5
  module Performance
6
- # This cop identifies unnecessary use of a regex where
7
- # `String#include?` would suffice.
6
+ # Identifies unnecessary use of a regex where `String#include?` would suffice.
8
7
  #
9
8
  # @safety
10
- # This cop's offenses are not safe to auto-correct if a receiver is nil.
9
+ # This cop's offenses are not safe to autocorrect if a receiver is nil or a Symbol.
11
10
  #
12
11
  # @example
13
12
  # # bad
14
- # 'abc'.match?(/ab/)
15
- # /ab/.match?('abc')
16
- # 'abc' =~ /ab/
17
- # /ab/ =~ 'abc'
18
- # 'abc'.match(/ab/)
19
- # /ab/.match('abc')
13
+ # str.match?(/ab/)
14
+ # /ab/.match?(str)
15
+ # str =~ /ab/
16
+ # /ab/ =~ str
17
+ # str.match(/ab/)
18
+ # /ab/.match(str)
20
19
  #
21
20
  # # good
22
- # 'abc'.include?('ab')
21
+ # str.include?('ab')
23
22
  class StringInclude < Base
24
23
  extend AutoCorrector
25
24
 
26
- MSG = 'Use `String#include?` instead of a regex match with literal-only pattern.'
27
- RESTRICT_ON_SEND = %i[match =~ match?].freeze
25
+ MSG = 'Use `%<negation>sString#include?` instead of a regex match with literal-only pattern.'
26
+ RESTRICT_ON_SEND = %i[match =~ !~ match?].freeze
28
27
 
29
28
  def_node_matcher :redundant_regex?, <<~PATTERN
30
- {(send $!nil? {:match :=~ :match?} (regexp (str $#literal?) (regopt)))
31
- (send (regexp (str $#literal?) (regopt)) {:match :match?} $str)
29
+ {(call $!nil? {:match :=~ :!~ :match?} (regexp (str $#literal?) (regopt)))
30
+ (send (regexp (str $#literal?) (regopt)) {:match :match?} $_)
32
31
  (match-with-lvasgn (regexp (str $#literal?) (regopt)) $_)}
33
32
  PATTERN
34
33
 
34
+ # rubocop:disable Metrics/AbcSize
35
35
  def on_send(node)
36
36
  return unless (receiver, regex_str = redundant_regex?(node))
37
37
 
38
- add_offense(node) do |corrector|
38
+ negation = node.send_type? && node.method?(:!~)
39
+ message = format(MSG, negation: ('!' if negation))
40
+
41
+ add_offense(node, message: message) do |corrector|
39
42
  receiver, regex_str = regex_str, receiver if receiver.is_a?(String)
40
43
  regex_str = interpret_string_escapes(regex_str)
44
+ dot = node.loc.dot ? node.loc.dot.source : '.'
41
45
 
42
- new_source = "#{receiver.source}.include?(#{to_string_literal(regex_str)})"
46
+ new_source = "#{'!' if negation}#{receiver.source}#{dot}include?(#{to_string_literal(regex_str)})"
43
47
 
44
- corrector.replace(node.source_range, new_source)
48
+ corrector.replace(node, new_source)
45
49
  end
46
50
  end
51
+ # rubocop:enable Metrics/AbcSize
52
+ alias on_csend on_send
47
53
  alias on_match_with_lvasgn on_send
48
54
 
49
55
  private
@@ -3,8 +3,7 @@
3
3
  module RuboCop
4
4
  module Cop
5
5
  module Performance
6
- # This cop identifies places where `gsub` can be replaced by
7
- # `tr` or `delete`.
6
+ # Identifies places where `gsub` can be replaced by `tr` or `delete`.
8
7
  #
9
8
  # @example
10
9
  # # bad
@@ -30,7 +29,7 @@ module RuboCop
30
29
  BANG = '!'
31
30
 
32
31
  def_node_matcher :string_replacement?, <<~PATTERN
33
- (send _ {:gsub :gsub!}
32
+ (call _ {:gsub :gsub!}
34
33
  ${regexp str (send (const nil? :Regexp) {:new :compile} _)}
35
34
  $str)
36
35
  PATTERN
@@ -43,6 +42,7 @@ module RuboCop
43
42
  offense(node, first_param, second_param)
44
43
  end
45
44
  end
45
+ alias on_csend on_send
46
46
 
47
47
  private
48
48
 
@@ -71,7 +71,7 @@ module RuboCop
71
71
  replacement_method = replacement_method(node, first_source, second_source)
72
72
 
73
73
  corrector.replace(node.loc.selector, replacement_method)
74
- corrector.replace(first_param.source_range, to_string_literal(first_source)) unless first_param.str_type?
74
+ corrector.replace(first_param, to_string_literal(first_source)) unless first_param.str_type?
75
75
 
76
76
  remove_second_param(corrector, node, first_param) if second_source.empty? && first_source.length == 1
77
77
  end
@@ -87,8 +87,7 @@ module RuboCop
87
87
 
88
88
  unless first_param.str_type?
89
89
  return true if options
90
- return true unless first_source.is_a?(String) &&
91
- first_source =~ DETERMINISTIC_REGEX
90
+ return true unless first_source.is_a?(String) && first_source =~ DETERMINISTIC_REGEX
92
91
 
93
92
  # This must be done after checking DETERMINISTIC_REGEX
94
93
  # Otherwise things like \s will trip us up
@@ -142,8 +141,7 @@ module RuboCop
142
141
  end
143
142
 
144
143
  def message(node, first_source, second_source)
145
- replacement_method =
146
- replacement_method(node, first_source, second_source)
144
+ replacement_method = replacement_method(node, first_source, second_source)
147
145
 
148
146
  format(MSG, prefer: replacement_method, current: node.method_name)
149
147
  end
@@ -153,8 +151,7 @@ module RuboCop
153
151
  end
154
152
 
155
153
  def remove_second_param(corrector, node, first_param)
156
- end_range = range_between(first_param.source_range.end_pos,
157
- node.source_range.end_pos)
154
+ end_range = range_between(first_param.source_range.end_pos, node.source_range.end_pos)
158
155
 
159
156
  corrector.replace(end_range, method_suffix(node))
160
157
  end
@@ -3,11 +3,11 @@
3
3
  module RuboCop
4
4
  module Cop
5
5
  module Performance
6
- # This cop identifies places where custom code finding the sum of elements
6
+ # Identifies places where custom code finding the sum of elements
7
7
  # in some Enumerable object can be replaced by `Enumerable#sum` method.
8
8
  #
9
9
  # @safety
10
- # Auto-corrections are unproblematic wherever an initial value is provided explicitly:
10
+ # Autocorrections are unproblematic wherever an initial value is provided explicitly:
11
11
  #
12
12
  # [source,ruby]
13
13
  # ----
@@ -43,7 +43,7 @@ module RuboCop
43
43
  #
44
44
  # @example OnlySumOrWithInitialValue: false (default)
45
45
  # # bad
46
- # [1, 2, 3].inject(:+) # Auto-corrections for cases without initial value are unsafe
46
+ # [1, 2, 3].inject(:+) # Autocorrections for cases without initial value are unsafe
47
47
  # [1, 2, 3].inject(&:+) # and will only be performed when using the `-A` option.
48
48
  # [1, 2, 3].reduce { |acc, elem| acc + elem } # They can be prohibited completely using `SafeAutoCorrect: true`.
49
49
  # [1, 2, 3].reduce(10, :+)
@@ -70,6 +70,9 @@ module RuboCop
70
70
  class Sum < Base
71
71
  include RangeHelp
72
72
  extend AutoCorrector
73
+ extend TargetRubyVersion
74
+
75
+ minimum_target_ruby_version 2.4
73
76
 
74
77
  MSG = 'Use `%<good_method>s` instead of `%<bad_method>s`.'
75
78
  MSG_IF_NO_INIT_VALUE =
@@ -180,7 +183,7 @@ module RuboCop
180
183
  end
181
184
 
182
185
  def sum_method_range(node)
183
- range_between(node.loc.selector.begin_pos, node.loc.expression.end_pos)
186
+ range_between(node.loc.selector.begin_pos, node.source_range.end_pos)
184
187
  end
185
188
 
186
189
  def sum_map_range(map, sum)
@@ -3,7 +3,7 @@
3
3
  module RuboCop
4
4
  module Cop
5
5
  module Performance
6
- # This cop checks for .times.map calls.
6
+ # Checks for .times.map calls.
7
7
  # In most cases such calls can be replaced
8
8
  # with an explicit array creation.
9
9
  #
@@ -32,8 +32,7 @@ module RuboCop
32
32
  class TimesMap < Base
33
33
  extend AutoCorrector
34
34
 
35
- MESSAGE = 'Use `Array.new(%<count>s)` with a block ' \
36
- 'instead of `.times.%<map_or_collect>s`'
35
+ MESSAGE = 'Use `Array.new(%<count>s)` with a block instead of `.times.%<map_or_collect>s`'
37
36
  MESSAGE_ONLY_IF = 'only if `%<count>s` is always 0 or more'
38
37
  RESTRICT_ON_SEND = %i[map collect].freeze
39
38
 
@@ -44,16 +43,16 @@ module RuboCop
44
43
  def on_block(node)
45
44
  check(node)
46
45
  end
46
+ alias on_numblock on_block
47
47
 
48
48
  private
49
49
 
50
50
  def check(node)
51
51
  times_map_call(node) do |map_or_collect, count|
52
52
  add_offense(node, message: message(map_or_collect, count)) do |corrector|
53
- replacement = "Array.new(#{count.source}" \
54
- "#{map_or_collect.arguments.map { |arg| ", #{arg.source}" }.join})"
53
+ replacement = "Array.new(#{count.source}#{map_or_collect.arguments.map { |arg| ", #{arg.source}" }.join})"
55
54
 
56
- corrector.replace(map_or_collect.loc.expression, replacement)
55
+ corrector.replace(map_or_collect, replacement)
57
56
  end
58
57
  end
59
58
  end
@@ -68,7 +67,7 @@ module RuboCop
68
67
  end
69
68
 
70
69
  def_node_matcher :times_map_call, <<~PATTERN
71
- {(block $(send (send $!nil? :times) {:map :collect}) ...)
70
+ {({block numblock} $(send (send $!nil? :times) {:map :collect}) ...)
72
71
  $(send (send $!nil? :times) {:map :collect} (block_pass ...))}
73
72
  PATTERN
74
73
  end
@@ -3,8 +3,7 @@
3
3
  module RuboCop
4
4
  module Cop
5
5
  module Performance
6
- # This cop identifies places where `URI::Parser.new`
7
- # can be replaced by `URI::DEFAULT_PARSER`.
6
+ # Identifies places where `URI::Parser.new` can be replaced by `URI::DEFAULT_PARSER`.
8
7
  #
9
8
  # @example
10
9
  # # bad
@@ -16,8 +15,7 @@ module RuboCop
16
15
  class UriDefaultParser < Base
17
16
  extend AutoCorrector
18
17
 
19
- MSG = 'Use `%<double_colon>sURI::DEFAULT_PARSER` instead of ' \
20
- '`%<double_colon>sURI::Parser.new`.'
18
+ MSG = 'Use `%<double_colon>sURI::DEFAULT_PARSER` instead of `%<double_colon>sURI::Parser.new`.'
21
19
  RESTRICT_ON_SEND = %i[new].freeze
22
20
 
23
21
  def_node_matcher :uri_parser_new?, <<~PATTERN
@@ -27,12 +25,12 @@ module RuboCop
27
25
  PATTERN
28
26
 
29
27
  def on_send(node)
30
- return unless uri_parser_new?(node) do |captured_value|
28
+ uri_parser_new?(node) do |captured_value|
31
29
  double_colon = captured_value ? '::' : ''
32
30
  message = format(MSG, double_colon: double_colon)
33
31
 
34
32
  add_offense(node, message: message) do |corrector|
35
- corrector.replace(node.loc.expression, "#{double_colon}URI::DEFAULT_PARSER")
33
+ corrector.replace(node, "#{double_colon}URI::DEFAULT_PARSER")
36
34
  end
37
35
  end
38
36
  end
@@ -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'
@@ -4,7 +4,7 @@ module RuboCop
4
4
  module Performance
5
5
  # This module holds the RuboCop Performance version information.
6
6
  module Version
7
- STRING = '1.13.3'
7
+ STRING = '1.19.0'
8
8
 
9
9
  def self.document_version
10
10
  STRING.match('\d+\.\d+').to_s
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.13.3
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: 2022-03-05 00:00:00.000000000 Z
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.13/
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:
@@ -134,14 +135,14 @@ required_ruby_version: !ruby/object:Gem::Requirement
134
135
  requirements:
135
136
  - - ">="
136
137
  - !ruby/object:Gem::Version
137
- version: 2.5.0
138
+ version: 2.7.0
138
139
  required_rubygems_version: !ruby/object:Gem::Requirement
139
140
  requirements:
140
141
  - - ">="
141
142
  - !ruby/object:Gem::Version
142
143
  version: '0'
143
144
  requirements: []
144
- rubygems_version: 3.3.3
145
+ rubygems_version: 3.5.0.dev
145
146
  signing_key:
146
147
  specification_version: 4
147
148
  summary: Automatic performance checking tool for Ruby code.