rubocop 1.69.1 → 1.70.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/LICENSE.txt +1 -1
- data/README.md +2 -2
- data/config/default.yml +19 -2
- data/lib/rubocop/cli/command/execute_runner.rb +3 -3
- data/lib/rubocop/config.rb +13 -4
- data/lib/rubocop/config_loader.rb +4 -0
- data/lib/rubocop/config_loader_resolver.rb +14 -3
- data/lib/rubocop/config_validator.rb +18 -8
- data/lib/rubocop/cop/autocorrect_logic.rb +31 -34
- data/lib/rubocop/cop/base.rb +6 -0
- data/lib/rubocop/cop/bundler/duplicated_gem.rb +1 -1
- data/lib/rubocop/cop/bundler/gem_comment.rb +1 -1
- data/lib/rubocop/cop/internal_affairs/cop_enabled.rb +85 -0
- data/lib/rubocop/cop/internal_affairs/node_type_predicate.rb +4 -3
- data/lib/rubocop/cop/internal_affairs/operator_keyword.rb +4 -2
- data/lib/rubocop/cop/internal_affairs.rb +1 -0
- data/lib/rubocop/cop/layout/argument_alignment.rb +1 -7
- data/lib/rubocop/cop/layout/empty_lines_around_access_modifier.rb +1 -0
- data/lib/rubocop/cop/layout/empty_lines_around_begin_body.rb +5 -6
- data/lib/rubocop/cop/layout/extra_spacing.rb +1 -1
- data/lib/rubocop/cop/layout/first_argument_indentation.rb +2 -7
- data/lib/rubocop/cop/layout/first_array_element_indentation.rb +2 -7
- data/lib/rubocop/cop/layout/first_hash_element_indentation.rb +1 -6
- data/lib/rubocop/cop/layout/hash_alignment.rb +6 -4
- data/lib/rubocop/cop/layout/heredoc_argument_closing_parenthesis.rb +1 -0
- data/lib/rubocop/cop/layout/line_continuation_leading_space.rb +11 -2
- data/lib/rubocop/cop/layout/line_continuation_spacing.rb +7 -1
- data/lib/rubocop/cop/layout/line_end_string_concatenation_indentation.rb +1 -1
- data/lib/rubocop/cop/layout/line_length.rb +1 -0
- data/lib/rubocop/cop/layout/multiline_method_argument_line_breaks.rb +24 -0
- data/lib/rubocop/cop/layout/redundant_line_break.rb +1 -1
- data/lib/rubocop/cop/layout/space_after_method_name.rb +1 -1
- data/lib/rubocop/cop/layout/space_around_operators.rb +3 -3
- data/lib/rubocop/cop/layout/trailing_whitespace.rb +5 -3
- data/lib/rubocop/cop/lint/constant_reassignment.rb +152 -0
- data/lib/rubocop/cop/lint/duplicate_set_element.rb +20 -7
- data/lib/rubocop/cop/lint/literal_in_interpolation.rb +11 -3
- data/lib/rubocop/cop/lint/nested_method_definition.rb +5 -1
- data/lib/rubocop/cop/lint/non_atomic_file_operation.rb +4 -2
- data/lib/rubocop/cop/lint/numeric_operation_with_constant_result.rb +6 -14
- data/lib/rubocop/cop/lint/shared_mutable_default.rb +65 -0
- data/lib/rubocop/cop/lint/syntax.rb +4 -1
- data/lib/rubocop/cop/lint/unescaped_bracket_in_regexp.rb +1 -4
- data/lib/rubocop/cop/lint/void.rb +3 -2
- data/lib/rubocop/cop/metrics/class_length.rb +9 -9
- data/lib/rubocop/cop/metrics/method_length.rb +8 -1
- data/lib/rubocop/cop/mixin/check_line_breakable.rb +7 -7
- data/lib/rubocop/cop/mixin/comments_help.rb +6 -1
- data/lib/rubocop/cop/mixin/dig_help.rb +1 -1
- data/lib/rubocop/cop/mixin/line_length_help.rb +5 -4
- data/lib/rubocop/cop/mixin/preceding_following_alignment.rb +46 -22
- data/lib/rubocop/cop/mixin/space_before_punctuation.rb +1 -1
- data/lib/rubocop/cop/mixin/statement_modifier.rb +1 -1
- data/lib/rubocop/cop/mixin/string_literals_help.rb +1 -1
- data/lib/rubocop/cop/naming/block_forwarding.rb +1 -1
- data/lib/rubocop/cop/naming/rescued_exceptions_variable_name.rb +1 -1
- data/lib/rubocop/cop/style/access_modifier_declarations.rb +32 -1
- data/lib/rubocop/cop/style/and_or.rb +1 -1
- data/lib/rubocop/cop/style/arguments_forwarding.rb +1 -4
- data/lib/rubocop/cop/style/block_delimiters.rb +8 -1
- data/lib/rubocop/cop/style/class_and_module_children.rb +5 -2
- data/lib/rubocop/cop/style/each_for_simple_loop.rb +3 -6
- data/lib/rubocop/cop/style/empty_else.rb +4 -2
- data/lib/rubocop/cop/style/empty_literal.rb +1 -1
- data/lib/rubocop/cop/style/empty_method.rb +1 -1
- data/lib/rubocop/cop/style/exact_regexp_match.rb +1 -2
- data/lib/rubocop/cop/style/exponential_notation.rb +1 -1
- data/lib/rubocop/cop/style/file_null.rb +20 -4
- data/lib/rubocop/cop/style/float_division.rb +8 -4
- data/lib/rubocop/cop/style/hash_except.rb +54 -67
- data/lib/rubocop/cop/style/hash_syntax.rb +5 -2
- data/lib/rubocop/cop/style/if_with_semicolon.rb +6 -4
- data/lib/rubocop/cop/style/it_assignment.rb +36 -0
- data/lib/rubocop/cop/style/method_call_with_args_parentheses/omit_parentheses.rb +11 -1
- data/lib/rubocop/cop/style/method_call_with_args_parentheses.rb +2 -0
- data/lib/rubocop/cop/style/method_call_without_args_parentheses.rb +1 -1
- data/lib/rubocop/cop/style/missing_else.rb +2 -0
- data/lib/rubocop/cop/style/multiple_comparison.rb +34 -22
- data/lib/rubocop/cop/style/mutable_constant.rb +1 -1
- data/lib/rubocop/cop/style/object_then.rb +13 -15
- data/lib/rubocop/cop/style/quoted_symbols.rb +1 -1
- data/lib/rubocop/cop/style/raise_args.rb +5 -3
- data/lib/rubocop/cop/style/random_with_offset.rb +3 -3
- data/lib/rubocop/cop/style/redundant_current_directory_in_path.rb +2 -1
- data/lib/rubocop/cop/style/redundant_initialize.rb +12 -3
- data/lib/rubocop/cop/style/redundant_line_continuation.rb +12 -9
- data/lib/rubocop/cop/style/redundant_parentheses.rb +1 -4
- data/lib/rubocop/cop/style/redundant_regexp_argument.rb +3 -0
- data/lib/rubocop/cop/style/redundant_self_assignment.rb +6 -5
- data/lib/rubocop/cop/style/safe_navigation.rb +1 -1
- data/lib/rubocop/cop/style/send_with_literal_method_name.rb +2 -1
- data/lib/rubocop/cop/style/single_line_do_end_block.rb +1 -2
- data/lib/rubocop/cop/style/single_line_methods.rb +2 -3
- data/lib/rubocop/cop/style/slicing_with_range.rb +40 -11
- data/lib/rubocop/cop/style/super_arguments.rb +63 -15
- data/lib/rubocop/cop/style/yoda_condition.rb +8 -4
- data/lib/rubocop/cop/style/yoda_expression.rb +1 -0
- data/lib/rubocop/cop/util.rb +9 -2
- data/lib/rubocop/formatter/formatter_set.rb +1 -1
- data/lib/rubocop/lsp/diagnostic.rb +189 -0
- data/lib/rubocop/lsp/logger.rb +2 -2
- data/lib/rubocop/lsp/routes.rb +7 -23
- data/lib/rubocop/lsp/runtime.rb +15 -49
- data/lib/rubocop/lsp/stdin_runner.rb +83 -0
- data/lib/rubocop/magic_comment.rb +3 -3
- data/lib/rubocop/path_util.rb +11 -8
- data/lib/rubocop/rspec/shared_contexts.rb +4 -1
- data/lib/rubocop/runner.rb +5 -6
- data/lib/rubocop/target_ruby.rb +15 -0
- data/lib/rubocop/version.rb +1 -1
- data/lib/rubocop.rb +3 -0
- data/lib/ruby_lsp/rubocop/addon.rb +78 -0
- data/lib/ruby_lsp/rubocop/wraps_built_in_lsp_runtime.rb +50 -0
- metadata +16 -8
@@ -55,12 +55,9 @@ module RuboCop
|
|
55
55
|
return if node.each_descendant(:dstr).any?
|
56
56
|
|
57
57
|
regexp_constructor(node) do |text|
|
58
|
-
|
58
|
+
parse_regexp(text.value)&.each_expression do |expr|
|
59
59
|
detect_offenses(text, expr)
|
60
60
|
end
|
61
|
-
rescue Regexp::Parser::ParserError
|
62
|
-
# Upon encountering an invalid regular expression,
|
63
|
-
# we aim to proceed and identify any remaining potential offenses.
|
64
61
|
end
|
65
62
|
end
|
66
63
|
|
@@ -113,7 +113,8 @@ module RuboCop
|
|
113
113
|
end
|
114
114
|
|
115
115
|
def check_expression(expr)
|
116
|
-
expr = expr.body if expr.if_type?
|
116
|
+
expr = expr.body if expr.if_type?
|
117
|
+
return unless expr
|
117
118
|
|
118
119
|
check_literal(expr)
|
119
120
|
check_var(expr)
|
@@ -229,7 +230,7 @@ module RuboCop
|
|
229
230
|
end
|
230
231
|
|
231
232
|
def autocorrect_void_expression(corrector, node)
|
232
|
-
return if node.parent.if_type?
|
233
|
+
return if node.parent.if_type?
|
233
234
|
|
234
235
|
corrector.remove(range_with_surrounding_space(range: node.source_range, side: :left))
|
235
236
|
end
|
@@ -51,15 +51,7 @@ module RuboCop
|
|
51
51
|
end
|
52
52
|
|
53
53
|
def on_casgn(node)
|
54
|
-
|
55
|
-
|
56
|
-
block_node = if parent&.assignment?
|
57
|
-
parent.expression
|
58
|
-
elsif parent&.parent&.masgn_type?
|
59
|
-
parent.parent.expression
|
60
|
-
else
|
61
|
-
node.expression
|
62
|
-
end
|
54
|
+
block_node = node.expression || find_expression_within_parent(node.parent)
|
63
55
|
|
64
56
|
return unless block_node.respond_to?(:class_definition?) && block_node.class_definition?
|
65
57
|
|
@@ -71,6 +63,14 @@ module RuboCop
|
|
71
63
|
def message(length, max_length)
|
72
64
|
format('Class has too many lines. [%<length>d/%<max>d]', length: length, max: max_length)
|
73
65
|
end
|
66
|
+
|
67
|
+
def find_expression_within_parent(parent)
|
68
|
+
if parent&.assignment?
|
69
|
+
parent.expression
|
70
|
+
elsif parent&.parent&.masgn_type?
|
71
|
+
parent.parent.expression
|
72
|
+
end
|
73
|
+
end
|
74
74
|
end
|
75
75
|
end
|
76
76
|
end
|
@@ -48,7 +48,7 @@ module RuboCop
|
|
48
48
|
LABEL = 'Method'
|
49
49
|
|
50
50
|
def on_def(node)
|
51
|
-
return if
|
51
|
+
return if allowed?(node.method_name)
|
52
52
|
|
53
53
|
check_code_length(node)
|
54
54
|
end
|
@@ -57,6 +57,9 @@ module RuboCop
|
|
57
57
|
def on_block(node)
|
58
58
|
return unless node.method?(:define_method)
|
59
59
|
|
60
|
+
method_name = node.send_node.first_argument
|
61
|
+
return if method_name.basic_literal? && allowed?(method_name.value)
|
62
|
+
|
60
63
|
check_code_length(node)
|
61
64
|
end
|
62
65
|
alias on_numblock on_block
|
@@ -66,6 +69,10 @@ module RuboCop
|
|
66
69
|
def cop_label
|
67
70
|
LABEL
|
68
71
|
end
|
72
|
+
|
73
|
+
def allowed?(method_name)
|
74
|
+
allowed_method?(method_name) || matches_allowed_pattern?(method_name)
|
75
|
+
end
|
69
76
|
end
|
70
77
|
end
|
71
78
|
end
|
@@ -43,7 +43,7 @@ module RuboCop
|
|
43
43
|
# (Note: Passes may not happen exactly in this sequence.)
|
44
44
|
module CheckLineBreakable
|
45
45
|
def extract_breakable_node(node, max)
|
46
|
-
if node.
|
46
|
+
if node.call_type?
|
47
47
|
return if chained_to_heredoc?(node)
|
48
48
|
|
49
49
|
args = process_args(node.arguments)
|
@@ -74,9 +74,9 @@ module RuboCop
|
|
74
74
|
def extract_first_element_over_column_limit(node, elements, max)
|
75
75
|
line = node.first_line
|
76
76
|
|
77
|
-
# If a `send` node is not parenthesized, don't move the first element, because it
|
77
|
+
# If a `send` or `csend` node is not parenthesized, don't move the first element, because it
|
78
78
|
# can result in changed behavior or a syntax error.
|
79
|
-
if node.
|
79
|
+
if node.call_type? && !node.parenthesized? && !first_argument_is_heredoc?(node)
|
80
80
|
elements = elements.drop(1)
|
81
81
|
end
|
82
82
|
|
@@ -98,10 +98,10 @@ module RuboCop
|
|
98
98
|
end
|
99
99
|
|
100
100
|
# @api private
|
101
|
-
# If a send node contains a heredoc argument, splitting cannot happen
|
101
|
+
# If a `send` or `csend` node contains a heredoc argument, splitting cannot happen
|
102
102
|
# after the heredoc or else it will cause a syntax error.
|
103
103
|
def shift_elements_for_heredoc_arg(node, elements, index)
|
104
|
-
return index unless node.
|
104
|
+
return index unless node.call_type? || node.array_type?
|
105
105
|
|
106
106
|
heredoc_index = elements.index { |arg| arg.respond_to?(:heredoc?) && arg.heredoc? }
|
107
107
|
return index unless heredoc_index
|
@@ -156,7 +156,7 @@ module RuboCop
|
|
156
156
|
|
157
157
|
if ancestor.hash_type? || ancestor.array_type?
|
158
158
|
elements = ancestor.children
|
159
|
-
elsif ancestor.
|
159
|
+
elsif ancestor.call_type?
|
160
160
|
elements = process_args(ancestor.arguments)
|
161
161
|
else
|
162
162
|
next
|
@@ -176,7 +176,7 @@ module RuboCop
|
|
176
176
|
return children_could_be_broken_up?(ancestor.children)
|
177
177
|
end
|
178
178
|
|
179
|
-
next unless ancestor.
|
179
|
+
next unless ancestor.call_type?
|
180
180
|
|
181
181
|
args = process_args(ancestor.arguments)
|
182
182
|
return children_could_be_broken_up?(args) if breakable_collection?(ancestor, args)
|
@@ -16,6 +16,8 @@ module RuboCop
|
|
16
16
|
end
|
17
17
|
|
18
18
|
def comments_in_range(node)
|
19
|
+
return [] unless node.source_range
|
20
|
+
|
19
21
|
start_line = node.source_range.line
|
20
22
|
end_line = find_end_line(node)
|
21
23
|
|
@@ -71,10 +73,13 @@ module RuboCop
|
|
71
73
|
node.else_branch.loc.line
|
72
74
|
elsif node.elsif?
|
73
75
|
node.each_ancestor(:if).find(&:if?).loc.end.line
|
76
|
+
elsif node.if? && node.parent && parentheses?(node.parent)
|
77
|
+
node.parent.loc.end.line
|
74
78
|
end
|
75
79
|
elsif node.block_type? || node.numblock_type?
|
76
80
|
node.loc.end.line
|
77
|
-
elsif (next_sibling = node.right_sibling) && next_sibling.is_a?(AST::Node)
|
81
|
+
elsif (next_sibling = node.right_sibling) && next_sibling.is_a?(AST::Node) &&
|
82
|
+
next_sibling.source_range
|
78
83
|
next_sibling.loc.line
|
79
84
|
elsif (parent = node.parent)
|
80
85
|
if parent.loc.respond_to?(:end) && parent.loc.end
|
@@ -37,12 +37,13 @@ module RuboCop
|
|
37
37
|
last_uri_match = match_uris(line).last
|
38
38
|
return nil unless last_uri_match
|
39
39
|
|
40
|
-
begin_position, end_position = last_uri_match.offset(0)
|
41
|
-
pos + indentation_difference(line)
|
42
|
-
end
|
43
|
-
|
40
|
+
begin_position, end_position = last_uri_match.offset(0)
|
44
41
|
end_position = extend_uri_end_position(line, end_position)
|
45
42
|
|
43
|
+
line_indentation_difference = indentation_difference(line)
|
44
|
+
begin_position += line_indentation_difference
|
45
|
+
end_position += line_indentation_difference
|
46
|
+
|
46
47
|
return nil if begin_position < max_line_length && end_position < max_line_length
|
47
48
|
|
48
49
|
begin_position...end_position
|
@@ -5,6 +5,10 @@ module RuboCop
|
|
5
5
|
# Common functionality for checking whether an AST node/token is aligned
|
6
6
|
# with something on a preceding or following line
|
7
7
|
module PrecedingFollowingAlignment
|
8
|
+
# Tokens that end with an `=`, as well as `<<`, that can be aligned together:
|
9
|
+
# `=`, `==`, `===`, `!=`, `<=`, `>=`, `<<` and operator assignment (`+=`, etc).
|
10
|
+
ASSIGNMENT_OR_COMPARISON_TOKENS = %i[tEQL tEQ tEQQ tNEQ tLEQ tGEQ tOP_ASGN tLSHFT].freeze
|
11
|
+
|
8
12
|
private
|
9
13
|
|
10
14
|
def allow_for_alignment?
|
@@ -19,16 +23,20 @@ module RuboCop
|
|
19
23
|
aligned_with_adjacent_line?(range, method(:aligned_operator?))
|
20
24
|
end
|
21
25
|
|
22
|
-
|
26
|
+
# Allows alignment with a preceding operator that ends with an `=`,
|
27
|
+
# including assignment and comparison operators.
|
28
|
+
def aligned_with_preceding_equals_operator(token)
|
23
29
|
preceding_line_range = token.line.downto(1)
|
24
30
|
|
25
|
-
|
31
|
+
aligned_with_equals_sign(token, preceding_line_range)
|
26
32
|
end
|
27
33
|
|
28
|
-
|
34
|
+
# Allows alignment with a subsequent operator that ends with an `=`,
|
35
|
+
# including assignment and comparison operators.
|
36
|
+
def aligned_with_subsequent_equals_operator(token)
|
29
37
|
subsequent_line_range = token.line.upto(processed_source.lines.length)
|
30
38
|
|
31
|
-
|
39
|
+
aligned_with_equals_sign(token, subsequent_line_range)
|
32
40
|
end
|
33
41
|
|
34
42
|
def aligned_with_adjacent_line?(range, predicate)
|
@@ -62,7 +70,7 @@ module RuboCop
|
|
62
70
|
next unless index
|
63
71
|
next if indent && indent != index
|
64
72
|
|
65
|
-
return yield(range, line)
|
73
|
+
return yield(range, line, lineno + 1)
|
66
74
|
end
|
67
75
|
false
|
68
76
|
end
|
@@ -74,12 +82,12 @@ module RuboCop
|
|
74
82
|
end.map(&:line)
|
75
83
|
end
|
76
84
|
|
77
|
-
def aligned_token?(range, line)
|
78
|
-
aligned_words?(range, line) ||
|
85
|
+
def aligned_token?(range, line, lineno)
|
86
|
+
aligned_words?(range, line) || aligned_equals_operator?(range, lineno)
|
79
87
|
end
|
80
88
|
|
81
|
-
def aligned_operator?(range, line)
|
82
|
-
aligned_identical?(range, line) ||
|
89
|
+
def aligned_operator?(range, line, lineno)
|
90
|
+
aligned_identical?(range, line) || aligned_equals_operator?(range, lineno)
|
83
91
|
end
|
84
92
|
|
85
93
|
def aligned_words?(range, line)
|
@@ -90,23 +98,42 @@ module RuboCop
|
|
90
98
|
token == line[left_edge, token.length]
|
91
99
|
end
|
92
100
|
|
93
|
-
def
|
94
|
-
|
95
|
-
|
101
|
+
def aligned_equals_operator?(range, lineno)
|
102
|
+
# Check that the operator is aligned with a previous assignment or comparison operator
|
103
|
+
# ie. an equals sign, an operator assignment (eg. `+=`), a comparison (`==`, `<=`, etc.).
|
104
|
+
# Since append operators (`<<`) are a type of assignment, they are allowed as well,
|
105
|
+
# despite not ending with a literal equals character.
|
106
|
+
line_range = processed_source.buffer.line_range(lineno)
|
107
|
+
return false unless line_range
|
108
|
+
|
109
|
+
# Find the specific token to avoid matching up to operators inside strings
|
110
|
+
operator_token = processed_source.tokens_within(line_range).detect do |token|
|
111
|
+
ASSIGNMENT_OR_COMPARISON_TOKENS.include?(token.type)
|
112
|
+
end
|
113
|
+
|
114
|
+
aligned_with_preceding_equals?(range, operator_token) ||
|
115
|
+
aligned_with_append_operator?(range, operator_token)
|
96
116
|
end
|
97
117
|
|
98
|
-
def
|
99
|
-
|
118
|
+
def aligned_with_preceding_equals?(range, token)
|
119
|
+
return false unless token
|
100
120
|
|
101
|
-
|
102
|
-
|
121
|
+
range.source[-1] == '=' && range.last_column == token.pos.last_column
|
122
|
+
end
|
123
|
+
|
124
|
+
def aligned_with_append_operator?(range, token)
|
125
|
+
return false unless token
|
126
|
+
|
127
|
+
((range.source == '<<' && token.equal_sign?) ||
|
128
|
+
(range.source[-1] == '=' && token.type == :tLSHFT)) &&
|
129
|
+
token && range.last_column == token.pos.last_column
|
103
130
|
end
|
104
131
|
|
105
132
|
def aligned_identical?(range, line)
|
106
133
|
range.source == line[range.column, range.size]
|
107
134
|
end
|
108
135
|
|
109
|
-
def
|
136
|
+
def aligned_with_equals_sign(token, line_range)
|
110
137
|
token_line_indent = processed_source.line_indentation(token.line)
|
111
138
|
assignment_lines = relevant_assignment_lines(line_range)
|
112
139
|
relevant_line_number = assignment_lines[1]
|
@@ -116,12 +143,9 @@ module RuboCop
|
|
116
143
|
relevant_indent = processed_source.line_indentation(relevant_line_number)
|
117
144
|
|
118
145
|
return :none if relevant_indent < token_line_indent
|
146
|
+
return :none unless processed_source.lines[relevant_line_number - 1]
|
119
147
|
|
120
|
-
|
121
|
-
|
122
|
-
return :none unless assignment_line
|
123
|
-
|
124
|
-
aligned_assignment?(token.pos, assignment_line) ? :yes : :no
|
148
|
+
aligned_equals_operator?(token.pos, relevant_line_number) ? :yes : :no
|
125
149
|
end
|
126
150
|
|
127
151
|
def assignment_lines
|
@@ -138,7 +138,7 @@ module RuboCop
|
|
138
138
|
def use_block_argument_as_local_variable?(node, last_argument)
|
139
139
|
return false if node.body.nil?
|
140
140
|
|
141
|
-
node.body.
|
141
|
+
node.body.each_node(:lvar, :lvasgn).any? do |lvar|
|
142
142
|
!lvar.parent.block_pass_type? && lvar.node_parts[0].to_s == last_argument
|
143
143
|
end
|
144
144
|
end
|
@@ -112,6 +112,26 @@ module RuboCop
|
|
112
112
|
# private attr :quux
|
113
113
|
#
|
114
114
|
# end
|
115
|
+
#
|
116
|
+
# @example AllowModifiersOnAliasMethod: true (default)
|
117
|
+
# # good
|
118
|
+
# class Foo
|
119
|
+
#
|
120
|
+
# public alias_method :bar, :foo
|
121
|
+
# protected alias_method :baz, :foo
|
122
|
+
# private alias_method :qux, :foo
|
123
|
+
#
|
124
|
+
# end
|
125
|
+
#
|
126
|
+
# @example AllowModifiersOnAliasMethod: false
|
127
|
+
# # bad
|
128
|
+
# class Foo
|
129
|
+
#
|
130
|
+
# public alias_method :bar, :foo
|
131
|
+
# protected alias_method :baz, :foo
|
132
|
+
# private alias_method :qux, :foo
|
133
|
+
#
|
134
|
+
# end
|
115
135
|
class AccessModifierDeclarations < Base
|
116
136
|
extend AutoCorrector
|
117
137
|
|
@@ -145,6 +165,12 @@ module RuboCop
|
|
145
165
|
(send nil? {:attr :attr_reader :attr_writer :attr_accessor} _+))
|
146
166
|
PATTERN
|
147
167
|
|
168
|
+
# @!method access_modifier_with_alias_method?, <<~PATTERN
|
169
|
+
def_node_matcher :access_modifier_with_alias_method?, <<~PATTERN
|
170
|
+
(send nil? {:private :protected :public :module_function}
|
171
|
+
(send nil? :alias_method _ _))
|
172
|
+
PATTERN
|
173
|
+
|
148
174
|
def on_send(node)
|
149
175
|
return if allowed?(node)
|
150
176
|
|
@@ -164,7 +190,8 @@ module RuboCop
|
|
164
190
|
!node.access_modifier? ||
|
165
191
|
ALLOWED_NODE_TYPES.include?(node.parent&.type) ||
|
166
192
|
allow_modifiers_on_symbols?(node) ||
|
167
|
-
allow_modifiers_on_attrs?(node)
|
193
|
+
allow_modifiers_on_attrs?(node) ||
|
194
|
+
allow_modifiers_on_alias_method?(node)
|
168
195
|
end
|
169
196
|
|
170
197
|
def autocorrect(corrector, node)
|
@@ -194,6 +221,10 @@ module RuboCop
|
|
194
221
|
cop_config['AllowModifiersOnAttrs'] && access_modifier_with_attr?(node)
|
195
222
|
end
|
196
223
|
|
224
|
+
def allow_modifiers_on_alias_method?(node)
|
225
|
+
cop_config['AllowModifiersOnAliasMethod'] && access_modifier_with_alias_method?(node)
|
226
|
+
end
|
227
|
+
|
197
228
|
def offense?(node)
|
198
229
|
(group_style? && access_modifier_is_inlined?(node) &&
|
199
230
|
!node.parent&.if_type? && !right_siblings_same_inline_method?(node)) ||
|
@@ -540,10 +540,7 @@ module RuboCop
|
|
540
540
|
end
|
541
541
|
|
542
542
|
def explicit_block_name?
|
543
|
-
|
544
|
-
return false unless block_forwarding_config['Enabled']
|
545
|
-
|
546
|
-
block_forwarding_config['EnforcedStyle'] == 'explicit'
|
543
|
+
config.for_enabled_cop('Naming/BlockForwarding')['EnforcedStyle'] == 'explicit'
|
547
544
|
end
|
548
545
|
end
|
549
546
|
end
|
@@ -183,7 +183,8 @@ module RuboCop
|
|
183
183
|
def on_send(node)
|
184
184
|
return unless node.arguments?
|
185
185
|
return if node.parenthesized?
|
186
|
-
return if node.
|
186
|
+
return if node.assignment_method?
|
187
|
+
return if single_argument_operator_method?(node)
|
187
188
|
|
188
189
|
node.arguments.each do |arg|
|
189
190
|
get_blocks(arg) do |block|
|
@@ -501,6 +502,12 @@ module RuboCop
|
|
501
502
|
# `begin`...`end` when changing `do-end` to `{}`.
|
502
503
|
block_node.each_child_node(:rescue, :ensure).any? && !block_node.single_line?
|
503
504
|
end
|
505
|
+
|
506
|
+
def single_argument_operator_method?(node)
|
507
|
+
return false unless node.operator_method?
|
508
|
+
|
509
|
+
node.arguments.one? && node.first_argument.block_type?
|
510
|
+
end
|
504
511
|
end
|
505
512
|
end
|
506
513
|
end
|
@@ -126,9 +126,12 @@ module RuboCop
|
|
126
126
|
end
|
127
127
|
|
128
128
|
def unindent(corrector, node)
|
129
|
-
return
|
129
|
+
return unless node.body.children.last
|
130
130
|
|
131
|
-
|
131
|
+
last_child_leading_spaces = leading_spaces(node.body.children.last)
|
132
|
+
return if leading_spaces(node).size == last_child_leading_spaces.size
|
133
|
+
|
134
|
+
column_delta = configured_indentation_width - last_child_leading_spaces.size
|
132
135
|
return if column_delta.zero?
|
133
136
|
|
134
137
|
AlignmentCorrector.correct(corrector, processed_source, node, column_delta)
|
@@ -53,8 +53,7 @@ module RuboCop
|
|
53
53
|
(block
|
54
54
|
(call
|
55
55
|
(begin
|
56
|
-
($
|
57
|
-
(int $_) (int $_)))
|
56
|
+
($range (int $_) (int $_)))
|
58
57
|
:each)
|
59
58
|
(args ...)
|
60
59
|
...)
|
@@ -65,8 +64,7 @@ module RuboCop
|
|
65
64
|
(block
|
66
65
|
(call
|
67
66
|
(begin
|
68
|
-
(
|
69
|
-
(int 0) (int _)))
|
67
|
+
(range (int 0) (int _)))
|
70
68
|
:each)
|
71
69
|
(args ...)
|
72
70
|
...)
|
@@ -77,8 +75,7 @@ module RuboCop
|
|
77
75
|
(block
|
78
76
|
(call
|
79
77
|
(begin
|
80
|
-
(
|
81
|
-
(int _) (int _)))
|
78
|
+
(range (int _) (int _)))
|
82
79
|
:each)
|
83
80
|
(args)
|
84
81
|
...)
|
@@ -131,6 +131,8 @@ module RuboCop
|
|
131
131
|
extend AutoCorrector
|
132
132
|
|
133
133
|
MSG = 'Redundant `else`-clause.'
|
134
|
+
NIL_STYLES = %i[nil both].freeze
|
135
|
+
EMPTY_STYLES = %i[empty both].freeze
|
134
136
|
|
135
137
|
def on_normal_if_unless(node)
|
136
138
|
check(node)
|
@@ -150,11 +152,11 @@ module RuboCop
|
|
150
152
|
end
|
151
153
|
|
152
154
|
def nil_style?
|
153
|
-
style
|
155
|
+
NIL_STYLES.include?(style)
|
154
156
|
end
|
155
157
|
|
156
158
|
def empty_style?
|
157
|
-
style
|
159
|
+
EMPTY_STYLES.include?(style)
|
158
160
|
end
|
159
161
|
|
160
162
|
def empty_check(node)
|
@@ -136,7 +136,7 @@ module RuboCop
|
|
136
136
|
def frozen_strings?
|
137
137
|
return true if frozen_string_literals_enabled?
|
138
138
|
|
139
|
-
frozen_string_cop_enabled = config.
|
139
|
+
frozen_string_cop_enabled = config.cop_enabled?('Style/FrozenStringLiteralComment')
|
140
140
|
frozen_string_cop_enabled &&
|
141
141
|
!frozen_string_literals_disabled? &&
|
142
142
|
string_literals_frozen_by_default?.nil?
|
@@ -40,8 +40,7 @@ module RuboCop
|
|
40
40
|
def on_send(node)
|
41
41
|
return unless (receiver = node.receiver)
|
42
42
|
return unless (regexp = exact_regexp_match(node))
|
43
|
-
|
44
|
-
parsed_regexp = Regexp::Parser.parse(regexp)
|
43
|
+
return unless (parsed_regexp = parse_regexp(regexp))
|
45
44
|
return unless exact_match_pattern?(parsed_regexp)
|
46
45
|
|
47
46
|
prefer = "#{receiver.source} #{new_method(node)} '#{parsed_regexp[1].text}'"
|
@@ -8,7 +8,7 @@ module RuboCop
|
|
8
8
|
#
|
9
9
|
# * `scientific` which enforces a mantissa between 1 (inclusive) and 10 (exclusive).
|
10
10
|
# * `engineering` which enforces the exponent to be a multiple of 3 and the mantissa
|
11
|
-
# to be between 0.1 (inclusive) and
|
11
|
+
# to be between 0.1 (inclusive) and 1000 (exclusive).
|
12
12
|
# * `integral` which enforces the mantissa to always be a whole number without
|
13
13
|
# trailing zeroes.
|
14
14
|
#
|
@@ -8,6 +8,12 @@ module RuboCop
|
|
8
8
|
# Only looks for full string matches, substrings within a longer string are not
|
9
9
|
# considered.
|
10
10
|
#
|
11
|
+
# However, only files that use the string `'/dev/null'` are targeted for detection.
|
12
|
+
# This is because the string `'NUL'` is not limited to the null device.
|
13
|
+
# This behavior results in false negatives when the `'/dev/null'` string is not used,
|
14
|
+
# but it is a trade-off to avoid false positives. `NULL:`
|
15
|
+
# Unlike `'NUL'`, `'NUL:'` is regarded as something like `C:` and is always detected.
|
16
|
+
#
|
11
17
|
# NOTE: Uses inside arrays and hashes are ignored.
|
12
18
|
#
|
13
19
|
# @safety
|
@@ -42,11 +48,21 @@ module RuboCop
|
|
42
48
|
REGEXP = %r{\A(/dev/null|NUL:?)\z}i.freeze
|
43
49
|
MSG = 'Use `File::NULL` instead of `%<source>s`.'
|
44
50
|
|
51
|
+
def on_new_investigation
|
52
|
+
return unless (ast = processed_source.ast)
|
53
|
+
|
54
|
+
@contain_dev_null_string_in_file = ast.each_descendant(:str).any? do |str|
|
55
|
+
content = str.str_content
|
56
|
+
|
57
|
+
valid_string?(content) && content.downcase == '/dev/null' # rubocop:disable Style/FileNull
|
58
|
+
end
|
59
|
+
end
|
60
|
+
|
45
61
|
def on_str(node)
|
46
62
|
value = node.value
|
47
|
-
|
48
|
-
return if invalid_string?(value)
|
63
|
+
return unless valid_string?(value)
|
49
64
|
return if acceptable?(node)
|
65
|
+
return if value.downcase == 'nul' && !@contain_dev_null_string_in_file # rubocop:disable Style/FileNull
|
50
66
|
return unless REGEXP.match?(value)
|
51
67
|
|
52
68
|
add_offense(node, message: format(MSG, source: value)) do |corrector|
|
@@ -56,8 +72,8 @@ module RuboCop
|
|
56
72
|
|
57
73
|
private
|
58
74
|
|
59
|
-
def
|
60
|
-
value.empty?
|
75
|
+
def valid_string?(value)
|
76
|
+
!value.empty? && value.valid_encoding?
|
61
77
|
end
|
62
78
|
|
63
79
|
def acceptable?(node)
|