rubocop 1.6.0 → 1.9.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 +3 -2
- data/config/default.yml +142 -19
- data/lib/rubocop.rb +15 -1
- data/lib/rubocop/cli/command/auto_genenerate_config.rb +5 -4
- data/lib/rubocop/comment_config.rb +6 -6
- data/lib/rubocop/config.rb +10 -7
- data/lib/rubocop/config_loader.rb +11 -14
- data/lib/rubocop/config_loader_resolver.rb +21 -4
- data/lib/rubocop/config_obsoletion.rb +5 -3
- data/lib/rubocop/config_obsoletion/extracted_cop.rb +6 -6
- data/lib/rubocop/config_store.rb +12 -1
- data/lib/rubocop/cop/base.rb +1 -1
- data/lib/rubocop/cop/gemspec/required_ruby_version.rb +3 -2
- data/lib/rubocop/cop/generator.rb +1 -3
- data/lib/rubocop/cop/internal_affairs.rb +6 -1
- data/lib/rubocop/cop/internal_affairs/empty_line_between_expect_offense_and_correction.rb +68 -0
- data/lib/rubocop/cop/internal_affairs/example_description.rb +89 -0
- data/lib/rubocop/cop/internal_affairs/redundant_described_class_as_subject.rb +61 -0
- data/lib/rubocop/cop/internal_affairs/redundant_let_rubocop_config_new.rb +64 -0
- data/lib/rubocop/cop/internal_affairs/style_detected_api_use.rb +145 -0
- data/lib/rubocop/cop/layout/class_structure.rb +7 -2
- data/lib/rubocop/cop/layout/empty_line_between_defs.rb +19 -3
- data/lib/rubocop/cop/layout/heredoc_argument_closing_parenthesis.rb +14 -0
- data/lib/rubocop/cop/layout/multiline_operation_indentation.rb +2 -2
- data/lib/rubocop/cop/layout/rescue_ensure_alignment.rb +3 -10
- data/lib/rubocop/cop/layout/space_around_equals_in_parameter_default.rb +1 -0
- data/lib/rubocop/cop/layout/space_before_block_braces.rb +2 -0
- data/lib/rubocop/cop/layout/space_before_brackets.rb +62 -0
- data/lib/rubocop/cop/layout/space_inside_block_braces.rb +13 -10
- data/lib/rubocop/cop/layout/space_inside_hash_literal_braces.rb +2 -2
- data/lib/rubocop/cop/lint/ambiguous_assignment.rb +59 -0
- data/lib/rubocop/cop/lint/binary_operator_with_identical_operands.rb +7 -2
- data/lib/rubocop/cop/lint/deprecated_constants.rb +75 -0
- data/lib/rubocop/cop/lint/duplicate_branch.rb +64 -2
- data/lib/rubocop/cop/lint/lambda_without_literal_block.rb +44 -0
- data/lib/rubocop/cop/lint/non_deterministic_require_order.rb +10 -6
- data/lib/rubocop/cop/lint/number_conversion.rb +41 -6
- data/lib/rubocop/cop/lint/numbered_parameter_assignment.rb +47 -0
- data/lib/rubocop/cop/lint/or_assignment_to_constant.rb +39 -0
- data/lib/rubocop/cop/lint/redundant_cop_disable_directive.rb +2 -1
- data/lib/rubocop/cop/lint/redundant_dir_glob_sort.rb +50 -0
- data/lib/rubocop/cop/lint/redundant_splat_expansion.rb +50 -17
- data/lib/rubocop/cop/lint/shadowed_exception.rb +1 -11
- data/lib/rubocop/cop/lint/symbol_conversion.rb +102 -0
- data/lib/rubocop/cop/lint/triple_quotes.rb +71 -0
- data/lib/rubocop/cop/lint/unreachable_loop.rb +17 -0
- data/lib/rubocop/cop/metrics/utils/code_length_calculator.rb +1 -1
- data/lib/rubocop/cop/mixin/allowed_identifiers.rb +18 -0
- data/lib/rubocop/cop/mixin/check_line_breakable.rb +5 -0
- data/lib/rubocop/cop/mixin/comments_help.rb +1 -11
- data/lib/rubocop/cop/mixin/first_element_line_break.rb +1 -1
- data/lib/rubocop/cop/mixin/uncommunicative_name.rb +5 -1
- data/lib/rubocop/cop/naming/memoized_instance_variable_name.rb +59 -5
- data/lib/rubocop/cop/naming/rescued_exceptions_variable_name.rb +38 -5
- data/lib/rubocop/cop/naming/variable_name.rb +2 -0
- data/lib/rubocop/cop/naming/variable_number.rb +2 -9
- data/lib/rubocop/cop/registry.rb +10 -0
- data/lib/rubocop/cop/severity.rb +3 -3
- data/lib/rubocop/cop/style/access_modifier_declarations.rb +3 -1
- data/lib/rubocop/cop/style/ascii_comments.rb +1 -1
- data/lib/rubocop/cop/style/collection_methods.rb +14 -1
- data/lib/rubocop/cop/style/commented_keyword.rb +22 -5
- data/lib/rubocop/cop/style/disable_cops_within_source_code_directive.rb +49 -9
- data/lib/rubocop/cop/style/empty_literal.rb +6 -2
- data/lib/rubocop/cop/style/endless_method.rb +102 -0
- data/lib/rubocop/cop/style/eval_with_location.rb +63 -34
- data/lib/rubocop/cop/style/explicit_block_argument.rb +10 -0
- data/lib/rubocop/cop/style/float_division.rb +3 -0
- data/lib/rubocop/cop/style/for.rb +2 -0
- data/lib/rubocop/cop/style/format_string_token.rb +18 -2
- data/lib/rubocop/cop/style/hash_except.rb +95 -0
- data/lib/rubocop/cop/style/hash_like_case.rb +2 -1
- data/lib/rubocop/cop/style/if_inside_else.rb +22 -10
- data/lib/rubocop/cop/style/if_with_boolean_literal_branches.rb +96 -0
- data/lib/rubocop/cop/style/keyword_parameters_order.rb +12 -2
- data/lib/rubocop/cop/style/lambda_call.rb +2 -1
- data/lib/rubocop/cop/style/method_call_with_args_parentheses.rb +7 -0
- data/lib/rubocop/cop/style/method_call_with_args_parentheses/omit_parentheses.rb +16 -6
- data/lib/rubocop/cop/style/method_def_parentheses.rb +7 -0
- data/lib/rubocop/cop/style/multiline_method_signature.rb +26 -1
- data/lib/rubocop/cop/style/multiline_when_then.rb +3 -1
- data/lib/rubocop/cop/style/mutable_constant.rb +13 -3
- data/lib/rubocop/cop/style/nested_parenthesized_calls.rb +4 -0
- data/lib/rubocop/cop/style/nil_comparison.rb +1 -0
- data/lib/rubocop/cop/style/non_nil_check.rb +23 -13
- data/lib/rubocop/cop/style/raise_args.rb +5 -2
- data/lib/rubocop/cop/style/redundant_argument.rb +7 -1
- data/lib/rubocop/cop/style/redundant_freeze.rb +8 -4
- data/lib/rubocop/cop/style/redundant_return.rb +1 -1
- data/lib/rubocop/cop/style/single_line_methods.rb +34 -2
- data/lib/rubocop/cop/style/sole_nested_conditional.rb +29 -5
- data/lib/rubocop/cop/style/string_concatenation.rb +1 -1
- data/lib/rubocop/cop/style/symbol_proc.rb +5 -4
- data/lib/rubocop/cop/style/ternary_parentheses.rb +1 -1
- data/lib/rubocop/cop/style/while_until_modifier.rb +2 -4
- data/lib/rubocop/cop/util.rb +3 -1
- data/lib/rubocop/formatter/git_hub_actions_formatter.rb +1 -0
- data/lib/rubocop/magic_comment.rb +30 -1
- data/lib/rubocop/options.rb +10 -10
- data/lib/rubocop/rspec/cop_helper.rb +0 -4
- data/lib/rubocop/rspec/expect_offense.rb +37 -22
- data/lib/rubocop/runner.rb +17 -1
- data/lib/rubocop/target_finder.rb +4 -2
- data/lib/rubocop/target_ruby.rb +47 -11
- data/lib/rubocop/util.rb +16 -0
- data/lib/rubocop/version.rb +8 -2
- metadata +26 -7
@@ -4,12 +4,15 @@ module RuboCop
|
|
4
4
|
module Cop
|
5
5
|
module Style
|
6
6
|
# This cop checks for comments put on the same line as some keywords.
|
7
|
-
# These keywords are: `
|
7
|
+
# These keywords are: `class`, `module`, `def`, `begin`, `end`.
|
8
8
|
#
|
9
9
|
# Note that some comments
|
10
10
|
# (`:nodoc:`, `:yields:`, `rubocop:disable` and `rubocop:todo`)
|
11
11
|
# are allowed.
|
12
12
|
#
|
13
|
+
# Auto-correction removes comments from `end` keyword and keeps comments
|
14
|
+
# for `class`, `module`, `def` and `begin` above the keyword.
|
15
|
+
#
|
13
16
|
# @example
|
14
17
|
# # bad
|
15
18
|
# if condition
|
@@ -34,16 +37,17 @@ module RuboCop
|
|
34
37
|
# y
|
35
38
|
# end
|
36
39
|
class CommentedKeyword < Base
|
40
|
+
include RangeHelp
|
41
|
+
extend AutoCorrector
|
42
|
+
|
37
43
|
MSG = 'Do not place comments on the same line as the ' \
|
38
44
|
'`%<keyword>s` keyword.'
|
39
45
|
|
40
46
|
def on_new_investigation
|
41
47
|
processed_source.comments.each do |comment|
|
42
|
-
next unless (match = line(comment).match(/(?<keyword>\S+).*#/))
|
48
|
+
next unless (match = line(comment).match(/(?<keyword>\S+).*#/)) && offensive?(comment)
|
43
49
|
|
44
|
-
|
45
|
-
add_offense(comment, message: format(MSG, keyword: match[:keyword]))
|
46
|
-
end
|
50
|
+
register_offense(comment, match[:keyword])
|
47
51
|
end
|
48
52
|
end
|
49
53
|
|
@@ -60,6 +64,19 @@ module RuboCop
|
|
60
64
|
].freeze
|
61
65
|
ALLOWED_COMMENT_REGEXES = ALLOWED_COMMENTS.map { |c| /#\s*#{c}/ }.freeze
|
62
66
|
|
67
|
+
def register_offense(comment, matched_keyword)
|
68
|
+
add_offense(comment, message: format(MSG, keyword: matched_keyword)) do |corrector|
|
69
|
+
range = range_with_surrounding_space(range: comment.loc.expression, newlines: false)
|
70
|
+
corrector.remove(range)
|
71
|
+
|
72
|
+
unless matched_keyword == 'end'
|
73
|
+
corrector.insert_before(
|
74
|
+
range.source_buffer.line_range(comment.loc.line), "#{comment.text}\n"
|
75
|
+
)
|
76
|
+
end
|
77
|
+
end
|
78
|
+
end
|
79
|
+
|
63
80
|
def offensive?(comment)
|
64
81
|
line = line(comment)
|
65
82
|
KEYWORD_REGEXES.any? { |r| r.match?(line) } &&
|
@@ -9,37 +9,77 @@ module RuboCop
|
|
9
9
|
# This is useful if want to make sure that every RuboCop error gets fixed
|
10
10
|
# and not quickly disabled with a comment.
|
11
11
|
#
|
12
|
+
# Specific cops can be allowed with the `AllowedCops` configuration. Note that
|
13
|
+
# if this configuration is set, `rubocop:disable all` is still disallowed.
|
14
|
+
#
|
12
15
|
# @example
|
13
16
|
# # bad
|
14
17
|
# # rubocop:disable Metrics/AbcSize
|
15
|
-
# def
|
18
|
+
# def foo
|
16
19
|
# end
|
17
20
|
# # rubocop:enable Metrics/AbcSize
|
18
21
|
#
|
19
22
|
# # good
|
20
|
-
# def
|
23
|
+
# def foo
|
24
|
+
# end
|
25
|
+
#
|
26
|
+
# @example AllowedCops: [Metrics/AbcSize]
|
27
|
+
# # good
|
28
|
+
# # rubocop:disable Metrics/AbcSize
|
29
|
+
# def foo
|
21
30
|
# end
|
31
|
+
# # rubocop:enable Metrics/AbcSize
|
22
32
|
#
|
23
33
|
class DisableCopsWithinSourceCodeDirective < Base
|
24
34
|
extend AutoCorrector
|
25
35
|
|
26
36
|
# rubocop:enable Lint/RedundantCopDisableDirective
|
27
|
-
MSG = '
|
37
|
+
MSG = 'Rubocop disable/enable directives are not permitted.'
|
38
|
+
MSG_FOR_COPS = 'Rubocop disable/enable directives for %<cops>s are not permitted.'
|
28
39
|
|
29
40
|
def on_new_investigation
|
30
41
|
processed_source.comments.each do |comment|
|
31
|
-
|
42
|
+
directive_cops = directive_cops(comment)
|
43
|
+
disallowed_cops = directive_cops - allowed_cops
|
32
44
|
|
33
|
-
|
34
|
-
|
35
|
-
|
45
|
+
next unless disallowed_cops.any?
|
46
|
+
|
47
|
+
register_offense(comment, directive_cops, disallowed_cops)
|
36
48
|
end
|
37
49
|
end
|
38
50
|
|
39
51
|
private
|
40
52
|
|
41
|
-
def
|
42
|
-
|
53
|
+
def register_offense(comment, directive_cops, disallowed_cops)
|
54
|
+
message = if any_cops_allowed?
|
55
|
+
format(MSG_FOR_COPS, cops: "`#{disallowed_cops.join('`, `')}`")
|
56
|
+
else
|
57
|
+
MSG
|
58
|
+
end
|
59
|
+
|
60
|
+
add_offense(comment, message: message) do |corrector|
|
61
|
+
replacement = ''
|
62
|
+
|
63
|
+
if directive_cops.length != disallowed_cops.length
|
64
|
+
replacement = comment.text.sub(/#{Regexp.union(disallowed_cops)},?\s*/, '')
|
65
|
+
.sub(/,\s*$/, '')
|
66
|
+
end
|
67
|
+
|
68
|
+
corrector.replace(comment, replacement)
|
69
|
+
end
|
70
|
+
end
|
71
|
+
|
72
|
+
def directive_cops(comment)
|
73
|
+
match = CommentConfig::COMMENT_DIRECTIVE_REGEXP.match(comment.text)
|
74
|
+
match[2] ? match[2].split(',').map(&:strip) : []
|
75
|
+
end
|
76
|
+
|
77
|
+
def allowed_cops
|
78
|
+
Array(cop_config['AllowedCops'])
|
79
|
+
end
|
80
|
+
|
81
|
+
def any_cops_allowed?
|
82
|
+
allowed_cops.any?
|
43
83
|
end
|
44
84
|
end
|
45
85
|
end
|
@@ -32,8 +32,12 @@ module RuboCop
|
|
32
32
|
def_node_matcher :str_node, '(send (const {nil? cbase} :String) :new)'
|
33
33
|
def_node_matcher :array_with_block,
|
34
34
|
'(block (send (const {nil? cbase} :Array) :new) args _)'
|
35
|
-
def_node_matcher :hash_with_block,
|
36
|
-
|
35
|
+
def_node_matcher :hash_with_block, <<~PATTERN
|
36
|
+
{
|
37
|
+
(block (send (const {nil? cbase} :Hash) :new) args _)
|
38
|
+
(numblock (send (const {nil? cbase} :Hash) :new) ...)
|
39
|
+
}
|
40
|
+
PATTERN
|
37
41
|
|
38
42
|
def on_send(node)
|
39
43
|
return unless (message = offense_message(node))
|
@@ -0,0 +1,102 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module RuboCop
|
4
|
+
module Cop
|
5
|
+
module Style
|
6
|
+
# This cop checks for endless methods.
|
7
|
+
#
|
8
|
+
# It can enforce either the use of endless methods definitions
|
9
|
+
# for single-lined method bodies, or disallow endless methods.
|
10
|
+
#
|
11
|
+
# Other method definition types are not considered by this cop.
|
12
|
+
#
|
13
|
+
# The supported styles are:
|
14
|
+
# * allow_single_line (default) - only single line endless method definitions are allowed.
|
15
|
+
# * allow_always - all endless method definitions are allowed.
|
16
|
+
# * disallow - all endless method definitions are disallowed.
|
17
|
+
#
|
18
|
+
# NOTE: Incorrect endless method definitions will always be
|
19
|
+
# corrected to a multi-line definition.
|
20
|
+
#
|
21
|
+
# @example EnforcedStyle: allow_single_line (default)
|
22
|
+
# # good
|
23
|
+
# def my_method() = x
|
24
|
+
#
|
25
|
+
# # bad, multi-line endless method
|
26
|
+
# def my_method() = x.foo
|
27
|
+
# .bar
|
28
|
+
# .baz
|
29
|
+
#
|
30
|
+
# @example EnforcedStyle: allow_always
|
31
|
+
# # good
|
32
|
+
# def my_method() = x
|
33
|
+
#
|
34
|
+
# # good
|
35
|
+
# def my_method() = x.foo
|
36
|
+
# .bar
|
37
|
+
# .baz
|
38
|
+
#
|
39
|
+
# @example EnforcedStyle: disallow
|
40
|
+
# # bad
|
41
|
+
# def my_method; x end
|
42
|
+
#
|
43
|
+
# # bad
|
44
|
+
# def my_method() = x.foo
|
45
|
+
# .bar
|
46
|
+
# .baz
|
47
|
+
#
|
48
|
+
class EndlessMethod < Base
|
49
|
+
include ConfigurableEnforcedStyle
|
50
|
+
extend TargetRubyVersion
|
51
|
+
extend AutoCorrector
|
52
|
+
|
53
|
+
minimum_target_ruby_version 3.0
|
54
|
+
|
55
|
+
CORRECTION_STYLES = %w[multiline single_line].freeze
|
56
|
+
MSG = 'Avoid endless method definitions.'
|
57
|
+
MSG_MULTI_LINE = 'Avoid endless method definitions with multiple lines.'
|
58
|
+
|
59
|
+
def on_def(node)
|
60
|
+
if style == :disallow
|
61
|
+
handle_disallow_style(node)
|
62
|
+
else
|
63
|
+
handle_allow_style(node)
|
64
|
+
end
|
65
|
+
end
|
66
|
+
|
67
|
+
private
|
68
|
+
|
69
|
+
def handle_allow_style(node)
|
70
|
+
return unless node.endless?
|
71
|
+
return if node.single_line? || style == :allow_always
|
72
|
+
|
73
|
+
add_offense(node, message: MSG_MULTI_LINE) do |corrector|
|
74
|
+
correct_to_multiline(corrector, node)
|
75
|
+
end
|
76
|
+
end
|
77
|
+
|
78
|
+
def handle_disallow_style(node)
|
79
|
+
return unless node.endless?
|
80
|
+
|
81
|
+
add_offense(node) do |corrector|
|
82
|
+
correct_to_multiline(corrector, node)
|
83
|
+
end
|
84
|
+
end
|
85
|
+
|
86
|
+
def correct_to_multiline(corrector, node)
|
87
|
+
replacement = <<~RUBY.strip
|
88
|
+
def #{node.method_name}#{arguments(node)}
|
89
|
+
#{node.body.source}
|
90
|
+
end
|
91
|
+
RUBY
|
92
|
+
|
93
|
+
corrector.replace(node, replacement)
|
94
|
+
end
|
95
|
+
|
96
|
+
def arguments(node, missing = '')
|
97
|
+
node.arguments.any? ? node.arguments.source : missing
|
98
|
+
end
|
99
|
+
end
|
100
|
+
end
|
101
|
+
end
|
102
|
+
end
|
@@ -3,9 +3,14 @@
|
|
3
3
|
module RuboCop
|
4
4
|
module Cop
|
5
5
|
module Style
|
6
|
-
# This cop
|
7
|
-
#
|
8
|
-
#
|
6
|
+
# This cop ensures that eval methods (`eval`, `instance_eval`, `class_eval`
|
7
|
+
# and `module_eval`) are given filename and line number values (`__FILE__`
|
8
|
+
# and `__LINE__`). This data is used to ensure that any errors raised
|
9
|
+
# within the evaluated code will be given the correct identification
|
10
|
+
# in a backtrace.
|
11
|
+
#
|
12
|
+
# The cop also checks that the line number given relative to `__LINE__` is
|
13
|
+
# correct.
|
9
14
|
#
|
10
15
|
# @example
|
11
16
|
# # bad
|
@@ -32,27 +37,17 @@ module RuboCop
|
|
32
37
|
# end
|
33
38
|
# RUBY
|
34
39
|
class EvalWithLocation < Base
|
35
|
-
MSG = 'Pass `__FILE__` and `__LINE__` to
|
36
|
-
|
37
|
-
|
38
|
-
'
|
40
|
+
MSG = 'Pass `__FILE__` and `__LINE__` to `%<method_name>s`.'
|
41
|
+
MSG_EVAL = 'Pass a binding, `__FILE__` and `__LINE__` to `eval`.'
|
42
|
+
MSG_INCORRECT_FILE = 'Incorrect file for `%<method_name>s`; ' \
|
43
|
+
'use `%<expected>s` instead of `%<actual>s`.'
|
44
|
+
MSG_INCORRECT_LINE = 'Incorrect line number for `%<method_name>s`; ' \
|
45
|
+
'use `%<expected>s` instead of `%<actual>s`.'
|
39
46
|
|
40
47
|
RESTRICT_ON_SEND = %i[eval class_eval module_eval instance_eval].freeze
|
41
48
|
|
42
|
-
def_node_matcher :
|
43
|
-
{
|
44
|
-
(send nil? :eval ${str dstr})
|
45
|
-
(send nil? :eval ${str dstr} _)
|
46
|
-
(send nil? :eval ${str dstr} _ #special_file_keyword?)
|
47
|
-
(send nil? :eval ${str dstr} _ #special_file_keyword? _)
|
48
|
-
|
49
|
-
(send _ {:class_eval :module_eval :instance_eval}
|
50
|
-
${str dstr})
|
51
|
-
(send _ {:class_eval :module_eval :instance_eval}
|
52
|
-
${str dstr} #special_file_keyword?)
|
53
|
-
(send _ {:class_eval :module_eval :instance_eval}
|
54
|
-
${str dstr} #special_file_keyword? _)
|
55
|
-
}
|
49
|
+
def_node_matcher :valid_eval_receiver?, <<~PATTERN
|
50
|
+
{ nil? (const {nil? cbase} :Kernel) }
|
56
51
|
PATTERN
|
57
52
|
|
58
53
|
def_node_matcher :line_with_offset?, <<~PATTERN
|
@@ -63,17 +58,31 @@ module RuboCop
|
|
63
58
|
PATTERN
|
64
59
|
|
65
60
|
def on_send(node)
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
|
71
|
-
|
61
|
+
# Classes should not redefine eval, but in case one does, it shouldn't
|
62
|
+
# register an offense. Only `eval` without a receiver and `Kernel.eval`
|
63
|
+
# are considered.
|
64
|
+
return if node.method?(:eval) && !valid_eval_receiver?(node.receiver)
|
65
|
+
|
66
|
+
code = node.arguments.first
|
67
|
+
return unless code.str_type? || code.dstr_type?
|
68
|
+
|
69
|
+
file, line = file_and_line(node)
|
70
|
+
|
71
|
+
if line
|
72
|
+
check_file(node, file)
|
73
|
+
check_line(node, code)
|
74
|
+
else
|
75
|
+
register_offense(node)
|
72
76
|
end
|
73
77
|
end
|
74
78
|
|
75
79
|
private
|
76
80
|
|
81
|
+
def register_offense(node)
|
82
|
+
msg = node.method?(:eval) ? MSG_EVAL : format(MSG, method_name: node.method_name)
|
83
|
+
add_offense(node, message: msg)
|
84
|
+
end
|
85
|
+
|
77
86
|
def special_file_keyword?(node)
|
78
87
|
node.str_type? &&
|
79
88
|
node.source == '__FILE__'
|
@@ -84,6 +93,11 @@ module RuboCop
|
|
84
93
|
node.source == '__LINE__'
|
85
94
|
end
|
86
95
|
|
96
|
+
def file_and_line(node)
|
97
|
+
base = node.method?(:eval) ? 2 : 1
|
98
|
+
[node.arguments[base], node.arguments[base + 1]]
|
99
|
+
end
|
100
|
+
|
87
101
|
# FIXME: It's a Style/ConditionalAssignment's false positive.
|
88
102
|
# rubocop:disable Style/ConditionalAssignment
|
89
103
|
def with_lineno?(node)
|
@@ -95,17 +109,32 @@ module RuboCop
|
|
95
109
|
end
|
96
110
|
# rubocop:enable Style/ConditionalAssignment
|
97
111
|
|
98
|
-
def message_incorrect_line(actual, sign, line_diff)
|
112
|
+
def message_incorrect_line(method_name, actual, sign, line_diff)
|
99
113
|
expected =
|
100
114
|
if line_diff.zero?
|
101
115
|
'__LINE__'
|
102
116
|
else
|
103
117
|
"__LINE__ #{sign} #{line_diff}"
|
104
118
|
end
|
105
|
-
|
119
|
+
|
120
|
+
format(MSG_INCORRECT_LINE,
|
121
|
+
method_name: method_name,
|
122
|
+
actual: actual.source,
|
123
|
+
expected: expected)
|
124
|
+
end
|
125
|
+
|
126
|
+
def check_file(node, file_node)
|
127
|
+
return true if special_file_keyword?(file_node)
|
128
|
+
|
129
|
+
message = format(MSG_INCORRECT_FILE,
|
130
|
+
method_name: node.method_name,
|
131
|
+
expected: '__FILE__',
|
132
|
+
actual: file_node.source)
|
133
|
+
|
134
|
+
add_offense(file_node, message: message)
|
106
135
|
end
|
107
136
|
|
108
|
-
def
|
137
|
+
def check_line(node, code)
|
109
138
|
line_node = node.arguments.last
|
110
139
|
lineno_range = line_node.loc.expression
|
111
140
|
line_diff = string_first_line(code) - lineno_range.first_line
|
@@ -124,22 +153,22 @@ module RuboCop
|
|
124
153
|
end
|
125
154
|
end
|
126
155
|
|
127
|
-
def add_offense_for_same_line(
|
156
|
+
def add_offense_for_same_line(node, line_node)
|
128
157
|
return if special_line_keyword?(line_node)
|
129
158
|
|
130
159
|
add_offense(
|
131
160
|
line_node.loc.expression,
|
132
|
-
message: message_incorrect_line(line_node, nil, 0)
|
161
|
+
message: message_incorrect_line(node.method_name, line_node, nil, 0)
|
133
162
|
)
|
134
163
|
end
|
135
164
|
|
136
|
-
def add_offense_for_different_line(
|
165
|
+
def add_offense_for_different_line(node, line_node, line_diff)
|
137
166
|
sign = line_diff.positive? ? :+ : :-
|
138
167
|
return if line_with_offset?(line_node, sign, line_diff.abs)
|
139
168
|
|
140
169
|
add_offense(
|
141
170
|
line_node.loc.expression,
|
142
|
-
message: message_incorrect_line(line_node, sign, line_diff.abs)
|
171
|
+
message: message_incorrect_line(node.method_name, line_node, sign, line_diff.abs)
|
143
172
|
)
|
144
173
|
end
|
145
174
|
end
|
@@ -6,6 +6,9 @@ module RuboCop
|
|
6
6
|
# This cop enforces the use of explicit block argument to avoid writing
|
7
7
|
# block literal that just passes its arguments to another block.
|
8
8
|
#
|
9
|
+
# NOTE: This cop only registers an offense if the block args match the
|
10
|
+
# yield args exactly.
|
11
|
+
#
|
9
12
|
# @example
|
10
13
|
# # bad
|
11
14
|
# def with_tmp_dir
|
@@ -75,7 +78,14 @@ module RuboCop
|
|
75
78
|
private
|
76
79
|
|
77
80
|
def yielding_arguments?(block_args, yield_args)
|
81
|
+
yield_args = yield_args.dup.fill(
|
82
|
+
nil,
|
83
|
+
yield_args.length, block_args.length - yield_args.length
|
84
|
+
)
|
85
|
+
|
78
86
|
yield_args.zip(block_args).all? do |yield_arg, block_arg|
|
87
|
+
next false unless yield_arg && block_arg
|
88
|
+
|
79
89
|
block_arg && yield_arg.children.first == block_arg.children.first
|
80
90
|
end
|
81
91
|
end
|