rubocop 1.56.0 → 1.56.1
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/lib/rubocop/cop/bundler/duplicated_group.rb +54 -8
- data/lib/rubocop/cop/correctors/lambda_literal_to_method_corrector.rb +7 -4
- data/lib/rubocop/cop/layout/leading_comment_space.rb +1 -1
- data/lib/rubocop/cop/layout/line_continuation_spacing.rb +1 -1
- data/lib/rubocop/cop/layout/redundant_line_break.rb +3 -1
- data/lib/rubocop/cop/lint/non_atomic_file_operation.rb +2 -2
- data/lib/rubocop/cop/lint/useless_assignment.rb +1 -2
- data/lib/rubocop/cop/naming/file_name.rb +1 -1
- data/lib/rubocop/cop/style/arguments_forwarding.rb +5 -4
- data/lib/rubocop/cop/style/concat_array_literals.rb +1 -1
- data/lib/rubocop/cop/style/method_call_with_args_parentheses/omit_parentheses.rb +3 -1
- data/lib/rubocop/cop/style/open_struct_use.rb +1 -1
- data/lib/rubocop/cop/style/redundant_parentheses.rb +3 -1
- data/lib/rubocop/cop/style/redundant_self_assignment_branch.rb +5 -0
- data/lib/rubocop/cop/style/symbol_array.rb +2 -0
- data/lib/rubocop/cop/utils/regexp_ranges.rb +26 -13
- data/lib/rubocop/target_ruby.rb +9 -5
- data/lib/rubocop/version.rb +1 -1
- metadata +5 -5
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 33c4c853e4bf651034a9ac3faa2f221baa77104521504824e2b4e88b349f01e0
|
4
|
+
data.tar.gz: d49422193353fc79c86b1c8cdfc3465f4abebf56bc01cd95d2c0e150c3f9747a
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 3bd1f56046aba375e89f62b8c954802636023539111238848c25b37a70ed95a41835198b2dd17ded64223b1f50e98f7e20f0c82aafed0381cad30f0be526b4fc
|
7
|
+
data.tar.gz: e02897c89f4869054ffea56efac2d9983f65bdce40c9254d5806effbda70561bf9c7c4161fa9a7d3269dc229d6d09b3e7c990eef10835f7ec5f2b3c55b32f6cf
|
@@ -5,6 +5,24 @@ module RuboCop
|
|
5
5
|
module Bundler
|
6
6
|
# A Gem group, or a set of groups, should be listed only once in a Gemfile.
|
7
7
|
#
|
8
|
+
# For example, if the values of `source`, `git`, `platforms`, or `path`
|
9
|
+
# surrounding `group` are different, no offense will be registered:
|
10
|
+
#
|
11
|
+
# [source,ruby]
|
12
|
+
# -----
|
13
|
+
# platforms :ruby do
|
14
|
+
# group :default do
|
15
|
+
# gem 'openssl'
|
16
|
+
# end
|
17
|
+
# end
|
18
|
+
#
|
19
|
+
# platforms :jruby do
|
20
|
+
# group :default do
|
21
|
+
# gem 'jruby-openssl'
|
22
|
+
# end
|
23
|
+
# end
|
24
|
+
# -----
|
25
|
+
#
|
8
26
|
# @example
|
9
27
|
# # bad
|
10
28
|
# group :development do
|
@@ -42,27 +60,35 @@ module RuboCop
|
|
42
60
|
|
43
61
|
MSG = 'Gem group `%<group_name>s` already defined on line ' \
|
44
62
|
'%<line_of_first_occurrence>d of the Gemfile.'
|
63
|
+
SOURCE_BLOCK_NAMES = %i[source git platforms path].freeze
|
64
|
+
|
65
|
+
# @!method group_declarations(node)
|
66
|
+
def_node_search :group_declarations, '(send nil? :group ...)'
|
45
67
|
|
46
68
|
def on_new_investigation
|
47
69
|
return if processed_source.blank?
|
48
70
|
|
49
71
|
duplicated_group_nodes.each do |nodes|
|
50
72
|
nodes[1..].each do |node|
|
51
|
-
|
73
|
+
group_name = node.arguments.map(&:source).join(', ')
|
74
|
+
|
75
|
+
register_offense(node, group_name, nodes.first.first_line)
|
52
76
|
end
|
53
77
|
end
|
54
78
|
end
|
55
79
|
|
56
80
|
private
|
57
81
|
|
58
|
-
# @!method group_declarations(node)
|
59
|
-
def_node_search :group_declarations, '(send nil? :group ...)'
|
60
|
-
|
61
82
|
def duplicated_group_nodes
|
62
|
-
group_declarations(processed_source.ast)
|
63
|
-
|
64
|
-
|
65
|
-
|
83
|
+
group_declarations = group_declarations(processed_source.ast)
|
84
|
+
group_keys = group_declarations.group_by do |node|
|
85
|
+
source_key = find_source_key(node)
|
86
|
+
group_attributes = group_attributes(node).sort.join
|
87
|
+
|
88
|
+
"#{source_key}#{group_attributes}"
|
89
|
+
end
|
90
|
+
|
91
|
+
group_keys.values.select { |nodes| nodes.size > 1 }
|
66
92
|
end
|
67
93
|
|
68
94
|
def register_offense(node, group_name, line_of_first_occurrence)
|
@@ -75,6 +101,26 @@ module RuboCop
|
|
75
101
|
)
|
76
102
|
add_offense(offense_location, message: message)
|
77
103
|
end
|
104
|
+
|
105
|
+
def find_source_key(node)
|
106
|
+
source_block = node.each_ancestor(:block).find do |block_node|
|
107
|
+
SOURCE_BLOCK_NAMES.include?(block_node.method_name)
|
108
|
+
end
|
109
|
+
|
110
|
+
return unless source_block
|
111
|
+
|
112
|
+
"#{source_block.method_name}#{source_block.send_node.first_argument&.source}"
|
113
|
+
end
|
114
|
+
|
115
|
+
def group_attributes(node)
|
116
|
+
node.arguments.map do |argument|
|
117
|
+
if argument.hash_type?
|
118
|
+
argument.pairs.map(&:source).sort.join(', ')
|
119
|
+
else
|
120
|
+
argument.value.to_s
|
121
|
+
end
|
122
|
+
end
|
123
|
+
end
|
78
124
|
end
|
79
125
|
end
|
80
126
|
end
|
@@ -14,12 +14,15 @@ module RuboCop
|
|
14
14
|
# Check for unparenthesized args' preceding and trailing whitespaces.
|
15
15
|
remove_unparenthesized_whitespace(corrector)
|
16
16
|
|
17
|
-
|
18
|
-
|
19
|
-
|
17
|
+
if block_node.block_type?
|
18
|
+
# Avoid correcting to `lambdado` by inserting whitespace
|
19
|
+
# if none exists before or after the lambda arguments.
|
20
|
+
insert_separating_space(corrector)
|
21
|
+
|
22
|
+
remove_arguments(corrector)
|
23
|
+
end
|
20
24
|
|
21
25
|
replace_selector(corrector)
|
22
|
-
remove_arguments(corrector)
|
23
26
|
|
24
27
|
replace_delimiters(corrector)
|
25
28
|
|
@@ -57,7 +57,7 @@ module RuboCop
|
|
57
57
|
|
58
58
|
def on_new_investigation
|
59
59
|
processed_source.comments.each do |comment|
|
60
|
-
next unless /\A#+[^#\s
|
60
|
+
next unless /\A(?!#\+\+|#--)(#+[^#\s=])/.match?(comment.text)
|
61
61
|
next if comment.loc.line == 1 && allowed_on_first_line?(comment)
|
62
62
|
next if doxygen_comment_style?(comment)
|
63
63
|
next if gemfile_ruby_comment?(comment)
|
@@ -109,7 +109,7 @@ module RuboCop
|
|
109
109
|
# rubocop:enable Metrics/AbcSize, Metrics/CyclomaticComplexity, Metrics/PerceivedComplexity
|
110
110
|
|
111
111
|
def comment_ranges(comments)
|
112
|
-
comments.map(&:
|
112
|
+
comments.map(&:source_range)
|
113
113
|
end
|
114
114
|
|
115
115
|
def last_line(processed_source)
|
@@ -118,7 +118,9 @@ module RuboCop
|
|
118
118
|
end
|
119
119
|
|
120
120
|
def comment_within?(node)
|
121
|
-
processed_source.comments.map
|
121
|
+
comment_line_numbers = processed_source.comments.map { |comment| comment.loc.line }
|
122
|
+
|
123
|
+
comment_line_numbers.any? do |comment_line_number|
|
122
124
|
comment_line_number >= node.first_line && comment_line_number <= node.last_line
|
123
125
|
end
|
124
126
|
end
|
@@ -57,12 +57,12 @@ module RuboCop
|
|
57
57
|
REMOVE_FORCE_METHODS).freeze
|
58
58
|
|
59
59
|
# @!method send_exist_node(node)
|
60
|
-
def_node_search :send_exist_node,
|
60
|
+
def_node_search :send_exist_node, <<~PATTERN
|
61
61
|
$(send (const nil? {:FileTest :File :Dir :Shell}) {:exist? :exists?} ...)
|
62
62
|
PATTERN
|
63
63
|
|
64
64
|
# @!method receiver_and_method_name(node)
|
65
|
-
def_node_matcher :receiver_and_method_name,
|
65
|
+
def_node_matcher :receiver_and_method_name, <<~PATTERN
|
66
66
|
(send (const nil? $_) $_ ...)
|
67
67
|
PATTERN
|
68
68
|
|
@@ -96,8 +96,7 @@ module RuboCop
|
|
96
96
|
return_value_node = return_value_node_of_scope(scope)
|
97
97
|
return unless assignment.meta_assignment_node.equal?(return_value_node)
|
98
98
|
|
99
|
-
" Use `#{assignment.operator.
|
100
|
-
"instead of `#{assignment.operator}`."
|
99
|
+
" Use `#{assignment.operator.delete_suffix('=')}` instead of `#{assignment.operator}`."
|
101
100
|
end
|
102
101
|
|
103
102
|
def similar_name_message(variable)
|
@@ -136,7 +136,7 @@ module RuboCop
|
|
136
136
|
end
|
137
137
|
|
138
138
|
def filename_good?(basename)
|
139
|
-
basename = basename.
|
139
|
+
basename = basename.delete_prefix('.')
|
140
140
|
basename = basename.sub(/\.[^.]+$/, '')
|
141
141
|
# special handling for Action Pack Variants file names like
|
142
142
|
# some_file.xlsx+mobile.axlsx
|
@@ -80,6 +80,7 @@ module RuboCop
|
|
80
80
|
minimum_target_ruby_version 2.7
|
81
81
|
|
82
82
|
FORWARDING_LVAR_TYPES = %i[splat kwsplat block_pass].freeze
|
83
|
+
ADDITIONAL_ARG_TYPES = %i[lvar arg].freeze
|
83
84
|
|
84
85
|
FORWARDING_MSG = 'Use shorthand syntax `...` for arguments forwarding.'
|
85
86
|
ARGS_MSG = 'Use anonymous positional arguments forwarding (`*`).'
|
@@ -212,7 +213,7 @@ module RuboCop
|
|
212
213
|
end
|
213
214
|
|
214
215
|
def arguments_range(node, first_node)
|
215
|
-
arguments = node.arguments
|
216
|
+
arguments = node.arguments.reject { |arg| ADDITIONAL_ARG_TYPES.include?(arg.type) }
|
216
217
|
|
217
218
|
start_node = first_node || arguments.first
|
218
219
|
|
@@ -279,7 +280,7 @@ module RuboCop
|
|
279
280
|
|
280
281
|
if can_forward_all?
|
281
282
|
:all
|
282
|
-
|
283
|
+
else
|
283
284
|
:rest_or_kwrest
|
284
285
|
end
|
285
286
|
end
|
@@ -332,9 +333,9 @@ module RuboCop
|
|
332
333
|
end
|
333
334
|
|
334
335
|
def no_post_splat_args?
|
335
|
-
splat_index = arguments.index(forwarded_rest_arg)
|
336
|
-
arg_after_splat = arguments[splat_index + 1]
|
336
|
+
return true unless (splat_index = arguments.index(forwarded_rest_arg))
|
337
337
|
|
338
|
+
arg_after_splat = arguments[splat_index + 1]
|
338
339
|
[nil, :hash, :block_pass].include?(arg_after_splat&.type)
|
339
340
|
end
|
340
341
|
|
@@ -146,7 +146,9 @@ module RuboCop
|
|
146
146
|
end
|
147
147
|
|
148
148
|
def call_in_match_pattern?(node)
|
149
|
-
node.parent
|
149
|
+
return false unless (parent = node.parent)
|
150
|
+
|
151
|
+
parent.match_pattern_type? || parent.match_pattern_p_type?
|
150
152
|
end
|
151
153
|
|
152
154
|
def hash_literal_in_arguments?(node)
|
@@ -45,7 +45,7 @@ module RuboCop
|
|
45
45
|
MSG = 'Avoid using `OpenStruct`; use `Struct`, `Hash`, a class or test doubles instead.'
|
46
46
|
|
47
47
|
# @!method uses_open_struct?(node)
|
48
|
-
def_node_matcher :uses_open_struct?,
|
48
|
+
def_node_matcher :uses_open_struct?, <<~PATTERN
|
49
49
|
(const {nil? (cbase)} :OpenStruct)
|
50
50
|
PATTERN
|
51
51
|
|
@@ -98,7 +98,9 @@ module RuboCop
|
|
98
98
|
end
|
99
99
|
|
100
100
|
def like_method_argument_parentheses?(node)
|
101
|
-
node.send_type? && node.
|
101
|
+
return false if !node.send_type? && !node.super_type? && !node.yield_type?
|
102
|
+
|
103
|
+
node.arguments.one? && !node.parenthesized? &&
|
102
104
|
!node.arithmetic_operation? && node.first_argument.begin_type?
|
103
105
|
end
|
104
106
|
|
@@ -75,6 +75,11 @@ module RuboCop
|
|
75
75
|
add_offense(offense_branch) do |corrector|
|
76
76
|
assignment_value = opposite_branch ? opposite_branch.source : 'nil'
|
77
77
|
replacement = "#{assignment_value} #{keyword} #{if_node.condition.source}"
|
78
|
+
if opposite_branch.respond_to?(:heredoc?) && opposite_branch.heredoc?
|
79
|
+
replacement += opposite_branch.loc.heredoc_end.with(
|
80
|
+
begin_pos: opposite_branch.source_range.end_pos
|
81
|
+
).source
|
82
|
+
end
|
78
83
|
|
79
84
|
corrector.replace(if_node, replacement)
|
80
85
|
end
|
@@ -69,6 +69,8 @@ module RuboCop
|
|
69
69
|
|
70
70
|
def complex_content?(node)
|
71
71
|
node.children.any? do |sym|
|
72
|
+
return false if DELIMITERS.include?(sym.source)
|
73
|
+
|
72
74
|
content = *sym
|
73
75
|
content = content.map { |c| c.is_a?(AST::Node) ? c.source : c }.join
|
74
76
|
content_without_delimiter_pairs = content.gsub(/(\[[^\s\[\]]*\])|(\([^\s\(\)]*\))/, '')
|
@@ -6,27 +6,40 @@ module RuboCop
|
|
6
6
|
# Helper to abstract complexity of building range pairs
|
7
7
|
# with octal escape reconstruction (needed for regexp_parser < 2.7).
|
8
8
|
class RegexpRanges
|
9
|
-
attr_reader :
|
9
|
+
attr_reader :root
|
10
10
|
|
11
11
|
def initialize(root)
|
12
12
|
@root = root
|
13
13
|
@compound_token = []
|
14
|
+
@pairs = []
|
15
|
+
@populated = false
|
16
|
+
end
|
17
|
+
|
18
|
+
def compound_token
|
19
|
+
populate_all unless @populated
|
20
|
+
|
21
|
+
@compound_token
|
14
22
|
end
|
15
23
|
|
16
24
|
def pairs
|
17
|
-
unless @
|
18
|
-
|
19
|
-
|
20
|
-
|
25
|
+
populate_all unless @populated
|
26
|
+
|
27
|
+
@pairs
|
28
|
+
end
|
29
|
+
|
30
|
+
private
|
31
|
+
|
32
|
+
def populate_all
|
33
|
+
populate(@root)
|
21
34
|
|
22
35
|
# If either bound is a compound the first one is an escape
|
23
36
|
# and that's all we need to work with.
|
24
37
|
# If there are any cops that wanted to operate on the compound
|
25
38
|
# expression we could wrap it with a facade class.
|
26
|
-
@pairs.map { |pair| pair.map(&:first) }
|
27
|
-
end
|
39
|
+
@pairs.map! { |pair| pair.map(&:first) }
|
28
40
|
|
29
|
-
|
41
|
+
@populated = true
|
42
|
+
end
|
30
43
|
|
31
44
|
def populate(expr)
|
32
45
|
expressions = expr.expressions.to_a
|
@@ -35,15 +48,15 @@ module RuboCop
|
|
35
48
|
current = expressions.shift
|
36
49
|
|
37
50
|
if escaped_octal?(current)
|
38
|
-
compound_token << current
|
39
|
-
compound_token.concat(pop_octal_digits(expressions))
|
51
|
+
@compound_token << current
|
52
|
+
@compound_token.concat(pop_octal_digits(expressions))
|
40
53
|
# If we have all the digits we can discard.
|
41
54
|
end
|
42
55
|
|
43
56
|
next unless current.type == :set
|
44
57
|
|
45
58
|
process_set(expressions, current)
|
46
|
-
compound_token.clear
|
59
|
+
@compound_token.clear
|
47
60
|
end
|
48
61
|
end
|
49
62
|
|
@@ -64,8 +77,8 @@ module RuboCop
|
|
64
77
|
|
65
78
|
def compose_range(expressions, current)
|
66
79
|
range_start, range_end = current.expressions
|
67
|
-
range_start = if compound_token.size.between?(1, 2) && octal_digit?(range_start.text)
|
68
|
-
compound_token.dup << range_start
|
80
|
+
range_start = if @compound_token.size.between?(1, 2) && octal_digit?(range_start.text)
|
81
|
+
@compound_token.dup << range_start
|
69
82
|
else
|
70
83
|
[range_start]
|
71
84
|
end
|
data/lib/rubocop/target_ruby.rb
CHANGED
@@ -155,9 +155,11 @@ module RuboCop
|
|
155
155
|
(send _ :required_ruby_version= $_)
|
156
156
|
PATTERN
|
157
157
|
|
158
|
-
# @!method
|
159
|
-
def_node_matcher :
|
160
|
-
(send (const(const _ :Gem):Requirement) :new
|
158
|
+
# @!method gem_requirement_versions(node)
|
159
|
+
def_node_matcher :gem_requirement_versions, <<~PATTERN
|
160
|
+
(send (const(const _ :Gem):Requirement) :new
|
161
|
+
{$str+ | (send $str :freeze)+ | (array $str+) | (array (send $str :freeze)+)}
|
162
|
+
)
|
161
163
|
PATTERN
|
162
164
|
|
163
165
|
def name
|
@@ -194,10 +196,12 @@ module RuboCop
|
|
194
196
|
end
|
195
197
|
|
196
198
|
def version_from_right_hand_side(right_hand_side)
|
199
|
+
gem_requirement_versions = gem_requirement_versions(right_hand_side)
|
200
|
+
|
197
201
|
if right_hand_side.array_type?
|
198
202
|
version_from_array(right_hand_side)
|
199
|
-
elsif
|
200
|
-
|
203
|
+
elsif gem_requirement_versions
|
204
|
+
gem_requirement_versions.map(&:value)
|
201
205
|
else
|
202
206
|
right_hand_side.value
|
203
207
|
end
|
data/lib/rubocop/version.rb
CHANGED
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: rubocop
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.56.
|
4
|
+
version: 1.56.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Bozhidar Batsov
|
@@ -10,7 +10,7 @@ authors:
|
|
10
10
|
autorequire:
|
11
11
|
bindir: exe
|
12
12
|
cert_chain: []
|
13
|
-
date: 2023-08-
|
13
|
+
date: 2023-08-21 00:00:00.000000000 Z
|
14
14
|
dependencies:
|
15
15
|
- !ruby/object:Gem::Dependency
|
16
16
|
name: base64
|
@@ -196,9 +196,9 @@ dependencies:
|
|
196
196
|
- - "<"
|
197
197
|
- !ruby/object:Gem::Version
|
198
198
|
version: '3.0'
|
199
|
-
description: |
|
200
|
-
|
201
|
-
|
199
|
+
description: |
|
200
|
+
RuboCop is a Ruby code style checking and code formatting tool.
|
201
|
+
It aims to enforce the community-driven Ruby Style Guide.
|
202
202
|
email: rubocop@googlegroups.com
|
203
203
|
executables:
|
204
204
|
- rubocop
|