rubocop 1.57.1 → 1.65.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 +4 -5
- data/assets/output.css.erb +159 -0
- data/assets/output.html.erb +1 -160
- data/config/default.yml +136 -19
- data/lib/rubocop/cached_data.rb +11 -3
- data/lib/rubocop/cli/command/auto_generate_config.rb +22 -8
- data/lib/rubocop/cli/command/lsp.rb +2 -2
- data/lib/rubocop/cli/command/show_docs_url.rb +2 -2
- data/lib/rubocop/cli.rb +10 -1
- data/lib/rubocop/config.rb +36 -12
- data/lib/rubocop/config_finder.rb +12 -2
- data/lib/rubocop/config_loader.rb +1 -2
- data/lib/rubocop/config_loader_resolver.rb +9 -3
- data/lib/rubocop/config_obsoletion.rb +11 -8
- data/lib/rubocop/config_validator.rb +14 -7
- data/lib/rubocop/cop/autocorrect_logic.rb +6 -1
- data/lib/rubocop/cop/base.rb +63 -16
- data/lib/rubocop/cop/bundler/gem_comment.rb +2 -2
- data/lib/rubocop/cop/bundler/gem_version.rb +3 -5
- data/lib/rubocop/cop/cop.rb +20 -2
- data/lib/rubocop/cop/correctors/each_to_for_corrector.rb +4 -8
- data/lib/rubocop/cop/correctors/for_to_each_corrector.rb +5 -13
- data/lib/rubocop/cop/documentation.rb +16 -6
- data/lib/rubocop/cop/exclude_limit.rb +1 -1
- data/lib/rubocop/cop/force.rb +12 -0
- data/lib/rubocop/cop/gemspec/add_runtime_dependency.rb +38 -0
- data/lib/rubocop/cop/gemspec/dependency_version.rb +3 -5
- data/lib/rubocop/cop/gemspec/deprecated_attribute_assignment.rb +2 -2
- data/lib/rubocop/cop/gemspec/duplicated_assignment.rb +2 -2
- data/lib/rubocop/cop/gemspec/required_ruby_version.rb +5 -1
- data/lib/rubocop/cop/gemspec/ruby_version_globals_usage.rb +3 -3
- data/lib/rubocop/cop/internal_affairs/example_description.rb +6 -5
- data/lib/rubocop/cop/internal_affairs/method_name_end_with.rb +8 -6
- data/lib/rubocop/cop/internal_affairs/method_name_equal.rb +19 -20
- data/lib/rubocop/cop/internal_affairs/node_first_or_last_argument.rb +53 -0
- data/lib/rubocop/cop/internal_affairs/node_matcher_directive.rb +123 -29
- data/lib/rubocop/cop/internal_affairs/redundant_expect_offense_arguments.rb +34 -0
- data/lib/rubocop/cop/internal_affairs.rb +2 -0
- data/lib/rubocop/cop/layout/argument_alignment.rb +1 -1
- data/lib/rubocop/cop/layout/case_indentation.rb +1 -1
- data/lib/rubocop/cop/layout/comment_indentation.rb +1 -1
- data/lib/rubocop/cop/layout/empty_comment.rb +3 -1
- data/lib/rubocop/cop/layout/empty_line_after_magic_comment.rb +14 -7
- data/lib/rubocop/cop/layout/empty_line_after_multiline_condition.rb +1 -1
- data/lib/rubocop/cop/layout/end_alignment.rb +15 -3
- data/lib/rubocop/cop/layout/extra_spacing.rb +4 -10
- data/lib/rubocop/cop/layout/first_argument_indentation.rb +2 -2
- data/lib/rubocop/cop/layout/first_array_element_indentation.rb +24 -7
- data/lib/rubocop/cop/layout/first_parameter_indentation.rb +1 -1
- data/lib/rubocop/cop/layout/heredoc_argument_closing_parenthesis.rb +2 -2
- data/lib/rubocop/cop/layout/heredoc_indentation.rb +2 -2
- data/lib/rubocop/cop/layout/indentation_width.rb +1 -1
- data/lib/rubocop/cop/layout/line_continuation_leading_space.rb +1 -1
- data/lib/rubocop/cop/layout/line_length.rb +20 -20
- data/lib/rubocop/cop/layout/redundant_line_break.rb +16 -3
- data/lib/rubocop/cop/layout/rescue_ensure_alignment.rb +4 -4
- data/lib/rubocop/cop/layout/single_line_block_chain.rb +5 -0
- data/lib/rubocop/cop/layout/space_around_operators.rb +53 -20
- data/lib/rubocop/cop/layout/space_before_block_braces.rb +19 -10
- data/lib/rubocop/cop/layout/space_inside_hash_literal_braces.rb +1 -1
- data/lib/rubocop/cop/layout/space_inside_string_interpolation.rb +3 -4
- data/lib/rubocop/cop/legacy/corrector.rb +12 -2
- data/lib/rubocop/cop/lint/assignment_in_condition.rb +6 -6
- data/lib/rubocop/cop/lint/binary_operator_with_identical_operands.rb +2 -2
- data/lib/rubocop/cop/lint/constant_overwritten_in_rescue.rb +1 -1
- data/lib/rubocop/cop/lint/debugger.rb +29 -3
- data/lib/rubocop/cop/lint/deprecated_class_methods.rb +1 -1
- data/lib/rubocop/cop/lint/duplicate_case_condition.rb +1 -1
- data/lib/rubocop/cop/lint/duplicate_methods.rb +1 -1
- data/lib/rubocop/cop/lint/empty_conditional_body.rb +2 -2
- data/lib/rubocop/cop/lint/empty_when.rb +1 -1
- data/lib/rubocop/cop/lint/erb_new_arguments.rb +24 -17
- data/lib/rubocop/cop/lint/float_comparison.rb +10 -0
- data/lib/rubocop/cop/lint/hash_compare_by_identity.rb +2 -1
- data/lib/rubocop/cop/lint/implicit_string_concatenation.rb +14 -7
- data/lib/rubocop/cop/lint/it_without_arguments_in_block.rb +56 -0
- data/lib/rubocop/cop/lint/literal_as_condition.rb +1 -1
- data/lib/rubocop/cop/lint/literal_assignment_in_condition.rb +85 -0
- data/lib/rubocop/cop/lint/mixed_case_range.rb +9 -4
- data/lib/rubocop/cop/lint/nested_method_definition.rb +1 -1
- data/lib/rubocop/cop/lint/next_without_accumulator.rb +6 -21
- data/lib/rubocop/cop/lint/non_deterministic_require_order.rb +3 -5
- data/lib/rubocop/cop/lint/number_conversion.rb +9 -4
- data/lib/rubocop/cop/lint/redundant_safe_navigation.rb +54 -6
- data/lib/rubocop/cop/lint/redundant_with_index.rb +6 -2
- data/lib/rubocop/cop/lint/redundant_with_object.rb +2 -2
- data/lib/rubocop/cop/lint/rescue_type.rb +1 -3
- data/lib/rubocop/cop/lint/safe_navigation_chain.rb +3 -4
- data/lib/rubocop/cop/lint/script_permission.rb +3 -3
- data/lib/rubocop/cop/lint/self_assignment.rb +38 -0
- data/lib/rubocop/cop/lint/shadowed_argument.rb +1 -0
- data/lib/rubocop/cop/lint/symbol_conversion.rb +7 -2
- data/lib/rubocop/cop/lint/syntax.rb +6 -3
- data/lib/rubocop/cop/lint/to_enum_arguments.rb +1 -3
- data/lib/rubocop/cop/lint/trailing_comma_in_attribute_declaration.rb +1 -1
- data/lib/rubocop/cop/lint/unmodified_reduce_accumulator.rb +3 -2
- data/lib/rubocop/cop/lint/unreachable_code.rb +4 -2
- data/lib/rubocop/cop/lint/unreachable_loop.rb +8 -2
- data/lib/rubocop/cop/lint/useless_access_modifier.rb +2 -2
- data/lib/rubocop/cop/lint/useless_times.rb +2 -2
- data/lib/rubocop/cop/lint/void.rb +53 -12
- data/lib/rubocop/cop/metrics/abc_size.rb +3 -3
- data/lib/rubocop/cop/metrics/block_nesting.rb +19 -7
- data/lib/rubocop/cop/metrics/class_length.rb +6 -1
- data/lib/rubocop/cop/metrics/utils/code_length_calculator.rb +5 -5
- data/lib/rubocop/cop/mixin/alignment.rb +5 -1
- data/lib/rubocop/cop/mixin/allowed_methods.rb +7 -1
- data/lib/rubocop/cop/mixin/allowed_pattern.rb +15 -3
- data/lib/rubocop/cop/mixin/check_line_breakable.rb +1 -1
- data/lib/rubocop/cop/mixin/code_length.rb +12 -1
- data/lib/rubocop/cop/mixin/comments_help.rb +16 -12
- data/lib/rubocop/cop/mixin/configurable_formatting.rb +1 -0
- data/lib/rubocop/cop/mixin/configurable_max.rb +5 -1
- data/lib/rubocop/cop/mixin/hash_shorthand_syntax.rb +23 -13
- data/lib/rubocop/cop/mixin/method_complexity.rb +15 -6
- data/lib/rubocop/cop/mixin/multiline_expression_indentation.rb +1 -1
- data/lib/rubocop/cop/mixin/preceding_following_alignment.rb +1 -1
- data/lib/rubocop/cop/mixin/rescue_node.rb +4 -0
- data/lib/rubocop/cop/mixin/safe_assignment.rb +1 -1
- data/lib/rubocop/cop/mixin/space_before_punctuation.rb +1 -1
- data/lib/rubocop/cop/naming/block_forwarding.rb +34 -7
- data/lib/rubocop/cop/naming/constant_name.rb +1 -2
- data/lib/rubocop/cop/naming/file_name.rb +2 -2
- data/lib/rubocop/cop/naming/inclusive_language.rb +1 -2
- data/lib/rubocop/cop/naming/memoized_instance_variable_name.rb +1 -1
- data/lib/rubocop/cop/naming/predicate_name.rb +2 -2
- data/lib/rubocop/cop/registry.rb +1 -1
- data/lib/rubocop/cop/security/compound_hash.rb +2 -2
- data/lib/rubocop/cop/security/open.rb +2 -2
- data/lib/rubocop/cop/style/access_modifier_declarations.rb +52 -2
- data/lib/rubocop/cop/style/accessor_grouping.rb +1 -1
- data/lib/rubocop/cop/style/alias.rb +1 -0
- data/lib/rubocop/cop/style/arguments_forwarding.rb +155 -21
- data/lib/rubocop/cop/style/array_first_last.rb +64 -0
- data/lib/rubocop/cop/style/auto_resource_cleanup.rb +21 -14
- data/lib/rubocop/cop/style/bisected_attr_accessor.rb +2 -2
- data/lib/rubocop/cop/style/case_like_if.rb +5 -5
- data/lib/rubocop/cop/style/class_check.rb +1 -0
- data/lib/rubocop/cop/style/class_vars.rb +3 -3
- data/lib/rubocop/cop/style/collection_compact.rb +21 -11
- data/lib/rubocop/cop/style/combinable_loops.rb +13 -7
- data/lib/rubocop/cop/style/commented_keyword.rb +5 -2
- data/lib/rubocop/cop/style/concat_array_literals.rb +1 -0
- data/lib/rubocop/cop/style/conditional_assignment.rb +7 -8
- data/lib/rubocop/cop/style/copyright.rb +31 -21
- data/lib/rubocop/cop/style/date_time.rb +5 -4
- data/lib/rubocop/cop/style/documentation.rb +24 -24
- data/lib/rubocop/cop/style/documentation_method.rb +20 -0
- data/lib/rubocop/cop/style/each_for_simple_loop.rb +7 -7
- data/lib/rubocop/cop/style/each_with_object.rb +2 -2
- data/lib/rubocop/cop/style/empty_literal.rb +1 -1
- data/lib/rubocop/cop/style/eval_with_location.rb +6 -15
- data/lib/rubocop/cop/style/exact_regexp_match.rb +4 -2
- data/lib/rubocop/cop/style/explicit_block_argument.rb +2 -2
- data/lib/rubocop/cop/style/for.rb +2 -0
- data/lib/rubocop/cop/style/format_string.rb +9 -9
- data/lib/rubocop/cop/style/hash_each_methods.rb +105 -11
- data/lib/rubocop/cop/style/hash_except.rb +10 -6
- data/lib/rubocop/cop/style/hash_syntax.rb +24 -2
- data/lib/rubocop/cop/style/identical_conditional_branches.rb +12 -1
- data/lib/rubocop/cop/style/if_with_boolean_literal_branches.rb +5 -3
- data/lib/rubocop/cop/style/inverse_methods.rb +14 -13
- data/lib/rubocop/cop/style/invertible_unless_condition.rb +44 -2
- data/lib/rubocop/cop/style/map_compact_with_conditional_block.rb +82 -50
- data/lib/rubocop/cop/style/map_into_array.rb +175 -0
- data/lib/rubocop/cop/style/map_to_hash.rb +18 -8
- data/lib/rubocop/cop/style/map_to_set.rb +1 -1
- data/lib/rubocop/cop/style/method_call_with_args_parentheses/omit_parentheses.rb +19 -5
- data/lib/rubocop/cop/style/method_call_with_args_parentheses.rb +2 -4
- data/lib/rubocop/cop/style/method_call_without_args_parentheses.rb +20 -0
- data/lib/rubocop/cop/style/method_def_parentheses.rb +1 -1
- data/lib/rubocop/cop/style/missing_respond_to_missing.rb +2 -2
- data/lib/rubocop/cop/style/multiline_method_signature.rb +10 -1
- data/lib/rubocop/cop/style/multiline_ternary_operator.rb +5 -3
- data/lib/rubocop/cop/style/next.rb +1 -1
- data/lib/rubocop/cop/style/nil_comparison.rb +2 -0
- data/lib/rubocop/cop/style/numeric_literal_prefix.rb +1 -1
- data/lib/rubocop/cop/style/numeric_predicate.rb +10 -2
- data/lib/rubocop/cop/style/object_then.rb +5 -3
- data/lib/rubocop/cop/style/one_line_conditional.rb +1 -1
- data/lib/rubocop/cop/style/operator_method_call.rb +2 -2
- data/lib/rubocop/cop/style/parallel_assignment.rb +3 -5
- data/lib/rubocop/cop/style/parentheses_around_condition.rb +8 -0
- data/lib/rubocop/cop/style/quoted_symbols.rb +1 -1
- data/lib/rubocop/cop/style/raise_args.rb +4 -1
- data/lib/rubocop/cop/style/redundant_argument.rb +27 -3
- data/lib/rubocop/cop/style/redundant_assignment.rb +10 -2
- data/lib/rubocop/cop/style/redundant_begin.rb +1 -1
- data/lib/rubocop/cop/style/redundant_current_directory_in_path.rb +5 -4
- data/lib/rubocop/cop/style/redundant_double_splat_hash_braces.rb +17 -10
- data/lib/rubocop/cop/style/redundant_each.rb +7 -4
- data/lib/rubocop/cop/style/redundant_fetch_block.rb +3 -3
- data/lib/rubocop/cop/style/redundant_file_extension_in_require.rb +1 -1
- data/lib/rubocop/cop/style/redundant_filter_chain.rb +5 -4
- data/lib/rubocop/cop/style/redundant_line_continuation.rb +19 -2
- data/lib/rubocop/cop/style/redundant_parentheses.rb +50 -19
- data/lib/rubocop/cop/style/redundant_percent_q.rb +1 -1
- data/lib/rubocop/cop/style/redundant_return.rb +7 -1
- data/lib/rubocop/cop/style/redundant_self.rb +17 -2
- data/lib/rubocop/cop/style/redundant_sort.rb +9 -8
- data/lib/rubocop/cop/style/redundant_sort_by.rb +2 -2
- data/lib/rubocop/cop/style/redundant_string_escape.rb +1 -1
- data/lib/rubocop/cop/style/require_order.rb +1 -1
- data/lib/rubocop/cop/style/sample.rb +3 -4
- data/lib/rubocop/cop/style/select_by_regexp.rb +7 -6
- data/lib/rubocop/cop/style/self_assignment.rb +1 -1
- data/lib/rubocop/cop/style/semicolon.rb +8 -0
- data/lib/rubocop/cop/style/send.rb +4 -4
- data/lib/rubocop/cop/style/send_with_literal_method_name.rb +104 -0
- data/lib/rubocop/cop/style/single_argument_dig.rb +7 -3
- data/lib/rubocop/cop/style/single_line_do_end_block.rb +3 -1
- data/lib/rubocop/cop/style/slicing_with_range.rb +76 -10
- data/lib/rubocop/cop/style/special_global_vars.rb +1 -2
- data/lib/rubocop/cop/style/string_chars.rb +1 -0
- data/lib/rubocop/cop/style/strip.rb +7 -4
- data/lib/rubocop/cop/style/super_arguments.rb +174 -0
- data/lib/rubocop/cop/style/super_with_args_parentheses.rb +35 -0
- data/lib/rubocop/cop/style/symbol_proc.rb +75 -5
- data/lib/rubocop/cop/style/top_level_method_definition.rb +1 -1
- data/lib/rubocop/cop/style/unpack_first.rb +11 -14
- data/lib/rubocop/cop/style/zero_length_predicate.rb +28 -24
- data/lib/rubocop/cop/team.rb +13 -0
- data/lib/rubocop/cop/util.rb +7 -1
- data/lib/rubocop/cop/utils/regexp_ranges.rb +1 -1
- data/lib/rubocop/cops_documentation_generator.rb +16 -4
- data/lib/rubocop/directive_comment.rb +10 -8
- data/lib/rubocop/ext/regexp_node.rb +9 -4
- data/lib/rubocop/ext/regexp_parser.rb +4 -21
- data/lib/rubocop/formatter/clang_style_formatter.rb +3 -7
- data/lib/rubocop/formatter/disabled_config_formatter.rb +23 -8
- data/lib/rubocop/formatter/formatter_set.rb +7 -1
- data/lib/rubocop/formatter/html_formatter.rb +37 -14
- data/lib/rubocop/formatter/json_formatter.rb +0 -1
- data/lib/rubocop/formatter/offense_count_formatter.rb +12 -2
- data/lib/rubocop/formatter/tap_formatter.rb +3 -7
- data/lib/rubocop/formatter.rb +1 -1
- data/lib/rubocop/lockfile.rb +56 -7
- data/lib/rubocop/lsp/logger.rb +1 -1
- data/lib/rubocop/lsp/routes.rb +12 -15
- data/lib/rubocop/lsp/runtime.rb +1 -1
- data/lib/rubocop/lsp/server.rb +7 -2
- data/lib/rubocop/lsp/severity.rb +1 -1
- data/lib/rubocop/lsp.rb +36 -0
- data/lib/rubocop/magic_comment.rb +1 -1
- data/lib/rubocop/options.rb +14 -11
- data/lib/rubocop/path_util.rb +6 -2
- data/lib/rubocop/rake_task.rb +1 -1
- data/lib/rubocop/result_cache.rb +0 -1
- data/lib/rubocop/rspec/cop_helper.rb +8 -2
- data/lib/rubocop/rspec/expect_offense.rb +16 -8
- data/lib/rubocop/rspec/shared_contexts.rb +73 -16
- data/lib/rubocop/rspec/support.rb +3 -0
- data/lib/rubocop/runner.rb +14 -3
- data/lib/rubocop/server/cache.rb +11 -2
- data/lib/rubocop/server/client_command/exec.rb +2 -3
- data/lib/rubocop/server/client_command/start.rb +1 -1
- data/lib/rubocop/server/core.rb +4 -0
- data/lib/rubocop/server/server_command/exec.rb +0 -1
- data/lib/rubocop/target_finder.rb +84 -78
- data/lib/rubocop/target_ruby.rb +82 -80
- data/lib/rubocop/version.rb +19 -4
- data/lib/rubocop.rb +8 -0
- metadata +27 -29
- /data/lib/rubocop/formatter/{git_hub_actions_formatter.rb → github_actions_formatter.rb} +0 -0
|
@@ -101,13 +101,11 @@ module RuboCop
|
|
|
101
101
|
Array(cop_config['AllowedGems'])
|
|
102
102
|
end
|
|
103
103
|
|
|
104
|
-
def message(
|
|
105
|
-
gem_specification = range.source
|
|
106
|
-
|
|
104
|
+
def message(_range)
|
|
107
105
|
if required_style?
|
|
108
|
-
|
|
106
|
+
REQUIRED_MSG
|
|
109
107
|
elsif forbidden_style?
|
|
110
|
-
|
|
108
|
+
FORBIDDEN_MSG
|
|
111
109
|
end
|
|
112
110
|
end
|
|
113
111
|
|
|
@@ -43,7 +43,7 @@ module RuboCop
|
|
|
43
43
|
def on_block(block_node)
|
|
44
44
|
return unless gem_specification(block_node)
|
|
45
45
|
|
|
46
|
-
block_parameter = block_node.
|
|
46
|
+
block_parameter = block_node.first_argument.source
|
|
47
47
|
|
|
48
48
|
assignment = block_node.descendants.detect do |node|
|
|
49
49
|
use_deprecated_attributes?(node, block_parameter)
|
|
@@ -65,7 +65,7 @@ module RuboCop
|
|
|
65
65
|
lhs, _op, _rhs = *node
|
|
66
66
|
[lhs, attribute]
|
|
67
67
|
else
|
|
68
|
-
[node, "#{attribute}="
|
|
68
|
+
[node, :"#{attribute}="]
|
|
69
69
|
end
|
|
70
70
|
end
|
|
71
71
|
|
|
@@ -31,8 +31,8 @@ module RuboCop
|
|
|
31
31
|
#
|
|
32
32
|
# # good
|
|
33
33
|
# Gem::Specification.new do |spec|
|
|
34
|
-
# spec.
|
|
35
|
-
# spec.
|
|
34
|
+
# spec.add_dependency('parallel', '~> 1.10')
|
|
35
|
+
# spec.add_dependency('parser', '>= 2.3.3.1', '< 3.0')
|
|
36
36
|
# end
|
|
37
37
|
class DuplicatedAssignment < Base
|
|
38
38
|
include RangeHelp
|
|
@@ -76,7 +76,9 @@ module RuboCop
|
|
|
76
76
|
PATTERN
|
|
77
77
|
|
|
78
78
|
def on_new_investigation
|
|
79
|
-
|
|
79
|
+
return if processed_source.ast && required_ruby_version?(processed_source.ast)
|
|
80
|
+
|
|
81
|
+
add_global_offense(MISSING_MSG)
|
|
80
82
|
end
|
|
81
83
|
|
|
82
84
|
def on_send(node)
|
|
@@ -110,6 +112,8 @@ module RuboCop
|
|
|
110
112
|
end
|
|
111
113
|
end
|
|
112
114
|
|
|
115
|
+
return unless required_ruby_version
|
|
116
|
+
|
|
113
117
|
required_ruby_version.str_content.scan(/\d/).first(2).join('.')
|
|
114
118
|
end
|
|
115
119
|
|
|
@@ -14,15 +14,15 @@ module RuboCop
|
|
|
14
14
|
# # bad
|
|
15
15
|
# Gem::Specification.new do |spec|
|
|
16
16
|
# if RUBY_VERSION >= '3.0'
|
|
17
|
-
# spec.
|
|
17
|
+
# spec.add_dependency 'gem_a'
|
|
18
18
|
# else
|
|
19
|
-
# spec.
|
|
19
|
+
# spec.add_dependency 'gem_b'
|
|
20
20
|
# end
|
|
21
21
|
# end
|
|
22
22
|
#
|
|
23
23
|
# # good
|
|
24
24
|
# Gem::Specification.new do |spec|
|
|
25
|
-
# spec.
|
|
25
|
+
# spec.add_dependency 'gem_a'
|
|
26
26
|
# end
|
|
27
27
|
#
|
|
28
28
|
class RubyVersionGlobalsUsage < Base
|
|
@@ -45,7 +45,8 @@ module RuboCop
|
|
|
45
45
|
EXPECT_OFFENSE_DESCRIPTION_MAPPING = {
|
|
46
46
|
/\A(does not|doesn't) (register|find|flag|report)/ => 'registers',
|
|
47
47
|
/\A(does not|doesn't) add (a|an|any )?offense/ => 'registers an offense',
|
|
48
|
-
/\
|
|
48
|
+
/\Aregisters no offense/ => 'registers an offense',
|
|
49
|
+
/\A(accepts|register)\b/ => 'registers'
|
|
49
50
|
}.freeze
|
|
50
51
|
|
|
51
52
|
EXPECT_NO_CORRECTIONS_DESCRIPTION_MAPPING = {
|
|
@@ -63,10 +64,10 @@ module RuboCop
|
|
|
63
64
|
expect_correction: EXPECT_CORRECTION_DESCRIPTION_MAPPING
|
|
64
65
|
}.freeze
|
|
65
66
|
|
|
66
|
-
# @!method offense_example
|
|
67
|
-
def_node_matcher :offense_example
|
|
67
|
+
# @!method offense_example(node)
|
|
68
|
+
def_node_matcher :offense_example, <<~PATTERN
|
|
68
69
|
(block
|
|
69
|
-
(send _ {:it :specify}
|
|
70
|
+
(send _ {:it :specify} $...)
|
|
70
71
|
_args
|
|
71
72
|
`(send nil? %RESTRICT_ON_SEND ...)
|
|
72
73
|
)
|
|
@@ -74,7 +75,7 @@ module RuboCop
|
|
|
74
75
|
|
|
75
76
|
def on_send(node)
|
|
76
77
|
parent = node.each_ancestor(:block).first
|
|
77
|
-
return unless parent && (current_description = offense_example
|
|
78
|
+
return unless parent && (current_description = offense_example(parent)&.first)
|
|
78
79
|
|
|
79
80
|
method_name = node.method_name
|
|
80
81
|
message = format(MSG, method_name: method_name)
|
|
@@ -30,6 +30,7 @@ module RuboCop
|
|
|
30
30
|
extend AutoCorrector
|
|
31
31
|
|
|
32
32
|
MSG = 'Use `%<method_name>s` instead of `%<method_suffix>s`.'
|
|
33
|
+
RESTRICT_ON_SEND = %i[end_with?].freeze
|
|
33
34
|
SUGGEST_METHOD_FOR_SUFFIX = {
|
|
34
35
|
'=' => 'assignment_method?',
|
|
35
36
|
'!' => 'bang_method?',
|
|
@@ -51,14 +52,15 @@ module RuboCop
|
|
|
51
52
|
|
|
52
53
|
def on_send(node)
|
|
53
54
|
method_name_end_with?(node) do |method_name_node, end_with_arg|
|
|
55
|
+
next unless method_name_node.receiver
|
|
56
|
+
|
|
57
|
+
preferred_method = SUGGEST_METHOD_FOR_SUFFIX[end_with_arg.value]
|
|
54
58
|
range = range(method_name_node, node)
|
|
55
|
-
message = format(
|
|
56
|
-
MSG,
|
|
57
|
-
method_name: SUGGEST_METHOD_FOR_SUFFIX[end_with_arg.value],
|
|
58
|
-
method_suffix: range.source
|
|
59
|
-
)
|
|
59
|
+
message = format(MSG, method_name: preferred_method, method_suffix: range.source)
|
|
60
60
|
|
|
61
|
-
add_offense(range, message: message)
|
|
61
|
+
add_offense(range, message: message) do |corrector|
|
|
62
|
+
corrector.replace(range, preferred_method)
|
|
63
|
+
end
|
|
62
64
|
end
|
|
63
65
|
end
|
|
64
66
|
alias on_csend on_send
|
|
@@ -12,38 +12,37 @@ module RuboCop
|
|
|
12
12
|
# # good
|
|
13
13
|
# node.method?(:do_something)
|
|
14
14
|
#
|
|
15
|
+
# # bad
|
|
16
|
+
# node.method_name != :do_something
|
|
17
|
+
#
|
|
18
|
+
# # good
|
|
19
|
+
# !node.method?(:do_something)
|
|
20
|
+
#
|
|
15
21
|
class MethodNameEqual < Base
|
|
16
|
-
include RangeHelp
|
|
17
22
|
extend AutoCorrector
|
|
18
23
|
|
|
19
|
-
MSG = 'Use
|
|
20
|
-
RESTRICT_ON_SEND = %i[==].freeze
|
|
24
|
+
MSG = 'Use `%<prefer>s` instead.'
|
|
25
|
+
RESTRICT_ON_SEND = %i[== !=].freeze
|
|
21
26
|
|
|
22
|
-
# @!method method_name
|
|
23
|
-
def_node_matcher :method_name
|
|
27
|
+
# @!method method_name(node)
|
|
28
|
+
def_node_matcher :method_name, <<~PATTERN
|
|
24
29
|
(send
|
|
25
|
-
|
|
26
|
-
(...) :method_name) :==
|
|
27
|
-
|
|
30
|
+
(send
|
|
31
|
+
(...) :method_name) {:== :!=}
|
|
32
|
+
$_)
|
|
28
33
|
PATTERN
|
|
29
34
|
|
|
30
35
|
def on_send(node)
|
|
31
|
-
method_name
|
|
32
|
-
|
|
36
|
+
method_name(node) do |method_name_arg|
|
|
37
|
+
bang = node.method?(:!=) ? '!' : ''
|
|
38
|
+
prefer = "#{bang}#{node.receiver.receiver.source}.method?(#{method_name_arg.source})"
|
|
39
|
+
message = format(MSG, prefer: prefer)
|
|
33
40
|
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
add_offense(range, message: message) do |corrector|
|
|
37
|
-
corrector.replace(range, "method?(#{method_name_arg.first.source})")
|
|
41
|
+
add_offense(node, message: message) do |corrector|
|
|
42
|
+
corrector.replace(node, prefer)
|
|
38
43
|
end
|
|
39
44
|
end
|
|
40
45
|
end
|
|
41
|
-
|
|
42
|
-
private
|
|
43
|
-
|
|
44
|
-
def range(method_name_node, node)
|
|
45
|
-
range_between(method_name_node.loc.selector.begin_pos, node.source_range.end_pos)
|
|
46
|
-
end
|
|
47
46
|
end
|
|
48
47
|
end
|
|
49
48
|
end
|
|
@@ -0,0 +1,53 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module RuboCop
|
|
4
|
+
module Cop
|
|
5
|
+
module InternalAffairs
|
|
6
|
+
# Checks for the use of `node.arguments.first` or `node.arguments.last` and
|
|
7
|
+
# suggests the use of `node.first_argument` or `node.last_argument` instead.
|
|
8
|
+
#
|
|
9
|
+
# @example
|
|
10
|
+
# # bad
|
|
11
|
+
# node.arguments.first
|
|
12
|
+
# node.arguments[0]
|
|
13
|
+
# node.arguments.last
|
|
14
|
+
# node.arguments[-1]
|
|
15
|
+
#
|
|
16
|
+
# # good
|
|
17
|
+
# node.first_argument
|
|
18
|
+
# node.last_argument
|
|
19
|
+
#
|
|
20
|
+
class NodeFirstOrLastArgument < Base
|
|
21
|
+
extend AutoCorrector
|
|
22
|
+
include RangeHelp
|
|
23
|
+
|
|
24
|
+
MSG = 'Use `#%<correct>s` instead of `#%<incorrect>s`.'
|
|
25
|
+
RESTRICT_ON_SEND = %i[arguments].freeze
|
|
26
|
+
|
|
27
|
+
# @!method arguments_first_or_last?(node)
|
|
28
|
+
def_node_matcher :arguments_first_or_last?, <<~PATTERN
|
|
29
|
+
{
|
|
30
|
+
(send (send !nil? :arguments) ${:first :last})
|
|
31
|
+
(send (send !nil? :arguments) :[] (int ${0 -1}))
|
|
32
|
+
}
|
|
33
|
+
PATTERN
|
|
34
|
+
|
|
35
|
+
def on_send(node)
|
|
36
|
+
arguments_first_or_last?(node.parent) do |end_or_index|
|
|
37
|
+
range = range_between(node.loc.selector.begin_pos, node.parent.source_range.end_pos)
|
|
38
|
+
correct = case end_or_index
|
|
39
|
+
when :first, 0 then 'first_argument'
|
|
40
|
+
when :last, -1 then 'last_argument'
|
|
41
|
+
else raise "Unknown end_or_index: #{end_or_index}"
|
|
42
|
+
end
|
|
43
|
+
message = format(MSG, correct: correct, incorrect: range.source)
|
|
44
|
+
|
|
45
|
+
add_offense(range, message: message) do |corrector|
|
|
46
|
+
corrector.replace(range, correct)
|
|
47
|
+
end
|
|
48
|
+
end
|
|
49
|
+
end
|
|
50
|
+
end
|
|
51
|
+
end
|
|
52
|
+
end
|
|
53
|
+
end
|
|
@@ -26,10 +26,18 @@ module RuboCop
|
|
|
26
26
|
MSG = 'Precede `%<method>s` with a `@!method` YARD directive.'
|
|
27
27
|
MSG_WRONG_NAME = '`@!method` YARD directive has invalid method name, ' \
|
|
28
28
|
'use `%<expected>s` instead of `%<actual>s`.'
|
|
29
|
+
MSG_MISSING_SCOPE_SELF = 'Follow the `@!method` YARD directive with ' \
|
|
30
|
+
'`@!scope class` if it is a class method.'
|
|
31
|
+
MSG_WRONG_SCOPE_SELF = 'Do not use the `@!scope class` YARD directive if it ' \
|
|
32
|
+
'is not a class method.'
|
|
29
33
|
MSG_TOO_MANY = 'Multiple `@!method` YARD directives found for this matcher.'
|
|
30
34
|
|
|
31
35
|
RESTRICT_ON_SEND = %i[def_node_matcher def_node_search].to_set.freeze
|
|
32
|
-
|
|
36
|
+
REGEXP_METHOD = /
|
|
37
|
+
^\s*\#\s*
|
|
38
|
+
@!method\s+(?<receiver>self\.)?(?<method_name>[a-z0-9_]+[?!]?)(?:\((?<args>.*)\))?
|
|
39
|
+
/x.freeze
|
|
40
|
+
REGEXP_SCOPE = /^\s*\#\s*@!scope class/.freeze
|
|
33
41
|
|
|
34
42
|
# @!method pattern_matcher?(node)
|
|
35
43
|
def_node_matcher :pattern_matcher?, <<~PATTERN
|
|
@@ -40,62 +48,131 @@ module RuboCop
|
|
|
40
48
|
return if node.arguments.none?
|
|
41
49
|
return unless valid_method_name?(node)
|
|
42
50
|
|
|
43
|
-
actual_name = node.
|
|
51
|
+
actual_name = node.first_argument.value.to_s
|
|
52
|
+
|
|
53
|
+
# Ignore cases where the method has a receiver that isn't self
|
|
54
|
+
return if actual_name.include?('.') && !actual_name.start_with?('self.')
|
|
55
|
+
|
|
44
56
|
directives = method_directives(node)
|
|
45
57
|
return too_many_directives(node) if directives.size > 1
|
|
46
58
|
|
|
47
|
-
|
|
48
|
-
return if directive_correct?(directive, actual_name)
|
|
49
|
-
|
|
50
|
-
register_offense(node, directive, actual_name)
|
|
59
|
+
process_directive(node, actual_name, directives.first)
|
|
51
60
|
end
|
|
52
61
|
|
|
53
62
|
private
|
|
54
63
|
|
|
55
64
|
def valid_method_name?(node)
|
|
56
|
-
node.
|
|
65
|
+
node.first_argument.str_type? || node.first_argument.sym_type?
|
|
57
66
|
end
|
|
58
67
|
|
|
59
68
|
def method_directives(node)
|
|
60
69
|
comments = processed_source.ast_with_comments[node]
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
match = comment.text.match(REGEXP)
|
|
70
|
+
group_comments(comments).filter_map do |comment_method, comment_scope|
|
|
71
|
+
match = comment_method.text.match(REGEXP_METHOD)
|
|
64
72
|
next unless match
|
|
65
73
|
|
|
66
|
-
{
|
|
74
|
+
{
|
|
75
|
+
node_method: comment_method,
|
|
76
|
+
node_scope: comment_scope,
|
|
77
|
+
method_name: match[:method_name],
|
|
78
|
+
args: match[:args],
|
|
79
|
+
receiver: match[:receiver],
|
|
80
|
+
has_scope_directive: comment_scope&.text&.match?(REGEXP_SCOPE)
|
|
81
|
+
}
|
|
82
|
+
end
|
|
83
|
+
end
|
|
84
|
+
|
|
85
|
+
def group_comments(comments)
|
|
86
|
+
result = []
|
|
87
|
+
comments.each.with_index do |comment, index|
|
|
88
|
+
# Grab the scope directive if it is preceded by a method directive
|
|
89
|
+
if comment.text.include?('@!method')
|
|
90
|
+
result << if (next_comment = comments[index + 1])&.text&.include?('@!scope')
|
|
91
|
+
[comment, next_comment]
|
|
92
|
+
else
|
|
93
|
+
[comment, nil]
|
|
94
|
+
end
|
|
95
|
+
end
|
|
67
96
|
end
|
|
97
|
+
result
|
|
68
98
|
end
|
|
69
99
|
|
|
70
100
|
def too_many_directives(node)
|
|
71
101
|
add_offense(node, message: MSG_TOO_MANY)
|
|
72
102
|
end
|
|
73
103
|
|
|
74
|
-
def
|
|
75
|
-
|
|
104
|
+
def process_directive(node, actual_name, directive)
|
|
105
|
+
return unless (offense_type = directive_offense_type(directive, actual_name))
|
|
106
|
+
|
|
107
|
+
register_offense(offense_type, node, directive, actual_name)
|
|
108
|
+
end
|
|
109
|
+
|
|
110
|
+
def directive_offense_type(directive, actual_name)
|
|
111
|
+
return :missing_directive unless directive
|
|
112
|
+
|
|
113
|
+
return :wrong_scope if wrong_scope(directive, actual_name)
|
|
114
|
+
return :no_scope if no_scope(directive, actual_name)
|
|
115
|
+
|
|
116
|
+
# The method directive being prefixed by 'self.' is always an offense.
|
|
117
|
+
# The matched method_name does not contain the receiver but the
|
|
118
|
+
# def_node_match method name may so it must be removed.
|
|
119
|
+
if directive[:method_name] != remove_receiver(actual_name) || directive[:receiver]
|
|
120
|
+
:wrong_name
|
|
121
|
+
end
|
|
122
|
+
end
|
|
123
|
+
|
|
124
|
+
def wrong_scope(directive, actual_name)
|
|
125
|
+
!actual_name.start_with?('self.') && directive[:has_scope_directive]
|
|
126
|
+
end
|
|
127
|
+
|
|
128
|
+
def no_scope(directive, actual_name)
|
|
129
|
+
actual_name.start_with?('self.') && !directive[:has_scope_directive]
|
|
76
130
|
end
|
|
77
131
|
|
|
78
|
-
def register_offense(node, directive, actual_name)
|
|
79
|
-
message = formatted_message(directive, actual_name, node.method_name)
|
|
132
|
+
def register_offense(offense_type, node, directive, actual_name)
|
|
133
|
+
message = formatted_message(offense_type, directive, actual_name, node.method_name)
|
|
80
134
|
|
|
81
135
|
add_offense(node, message: message) do |corrector|
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
136
|
+
case offense_type
|
|
137
|
+
when :wrong_name
|
|
138
|
+
correct_method_directive(corrector, directive, actual_name)
|
|
139
|
+
when :wrong_scope
|
|
140
|
+
remove_scope_directive(corrector, directive)
|
|
141
|
+
when :no_scope
|
|
142
|
+
insert_scope_directive(corrector, directive[:node_method])
|
|
143
|
+
when :missing_directive
|
|
144
|
+
insert_method_directive(corrector, node, actual_name)
|
|
86
145
|
end
|
|
87
146
|
end
|
|
88
147
|
end
|
|
89
148
|
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
149
|
+
# rubocop:disable Metrics/MethodLength
|
|
150
|
+
def formatted_message(offense_type, directive, actual_name, method_name)
|
|
151
|
+
case offense_type
|
|
152
|
+
when :wrong_name
|
|
153
|
+
# Add the receiver to the name when showing an offense
|
|
154
|
+
current_name = if directive[:receiver]
|
|
155
|
+
directive[:receiver] + directive[:method_name]
|
|
156
|
+
else
|
|
157
|
+
directive[:method_name]
|
|
158
|
+
end
|
|
159
|
+
# The correct name will never include a receiver, remove it
|
|
160
|
+
format(MSG_WRONG_NAME, expected: remove_receiver(actual_name), actual: current_name)
|
|
161
|
+
when :wrong_scope
|
|
162
|
+
MSG_WRONG_SCOPE_SELF
|
|
163
|
+
when :no_scope
|
|
164
|
+
MSG_MISSING_SCOPE_SELF
|
|
165
|
+
when :missing_directive
|
|
94
166
|
format(MSG, method: method_name)
|
|
95
167
|
end
|
|
96
168
|
end
|
|
169
|
+
# rubocop:enable Metrics/MethodLength
|
|
170
|
+
|
|
171
|
+
def remove_receiver(current)
|
|
172
|
+
current.delete_prefix('self.')
|
|
173
|
+
end
|
|
97
174
|
|
|
98
|
-
def
|
|
175
|
+
def insert_method_directive(corrector, node, actual_name)
|
|
99
176
|
# If the pattern matcher uses arguments (`%1`, `%2`, etc.), include them in the directive
|
|
100
177
|
arguments = pattern_arguments(node.arguments[1].source)
|
|
101
178
|
|
|
@@ -107,6 +184,14 @@ module RuboCop
|
|
|
107
184
|
corrector.insert_before(range, directive)
|
|
108
185
|
end
|
|
109
186
|
|
|
187
|
+
def insert_scope_directive(corrector, node)
|
|
188
|
+
range = range_with_surrounding_space(node.source_range, side: :left, newlines: false)
|
|
189
|
+
indentation = range.source.match(/^\s*/)[0]
|
|
190
|
+
directive = "\n#{indentation}# @!scope class"
|
|
191
|
+
|
|
192
|
+
corrector.insert_after(node, directive)
|
|
193
|
+
end
|
|
194
|
+
|
|
110
195
|
def pattern_arguments(pattern)
|
|
111
196
|
arguments = %w[node]
|
|
112
197
|
max_pattern_var = pattern.scan(/(?<=%)\d+/).map(&:to_i).max
|
|
@@ -134,12 +219,21 @@ module RuboCop
|
|
|
134
219
|
end
|
|
135
220
|
end
|
|
136
221
|
|
|
137
|
-
def
|
|
138
|
-
correct = "@!method #{actual_name}"
|
|
139
|
-
|
|
222
|
+
def correct_method_directive(corrector, directive, actual_name)
|
|
223
|
+
correct = "@!method #{remove_receiver(actual_name)}"
|
|
224
|
+
current_name = (directive[:receiver] || '') + directive[:method_name]
|
|
225
|
+
regexp = /@!method\s+#{Regexp.escape(current_name)}/
|
|
226
|
+
|
|
227
|
+
replacement = directive[:node_method].text.gsub(regexp, correct)
|
|
228
|
+
corrector.replace(directive[:node_method], replacement)
|
|
229
|
+
end
|
|
140
230
|
|
|
141
|
-
|
|
142
|
-
|
|
231
|
+
def remove_scope_directive(corrector, directive)
|
|
232
|
+
range = range_by_whole_lines(
|
|
233
|
+
directive[:node_scope].source_range,
|
|
234
|
+
include_final_newline: true
|
|
235
|
+
)
|
|
236
|
+
corrector.remove(range)
|
|
143
237
|
end
|
|
144
238
|
end
|
|
145
239
|
end
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module RuboCop
|
|
4
|
+
module Cop
|
|
5
|
+
module InternalAffairs
|
|
6
|
+
# Checks for redundant arguments of `RuboCop::RSpec::ExpectOffense`'s methods.
|
|
7
|
+
#
|
|
8
|
+
# @example
|
|
9
|
+
#
|
|
10
|
+
# # bad
|
|
11
|
+
# expect_no_offenses('code', keyword: keyword)
|
|
12
|
+
#
|
|
13
|
+
# # good
|
|
14
|
+
# expect_no_offenses('code')
|
|
15
|
+
#
|
|
16
|
+
class RedundantExpectOffenseArguments < Base
|
|
17
|
+
extend AutoCorrector
|
|
18
|
+
|
|
19
|
+
MSG = 'Remove the redundant arguments.'
|
|
20
|
+
RESTRICT_ON_SEND = %i[expect_no_offenses].freeze
|
|
21
|
+
|
|
22
|
+
def on_send(node)
|
|
23
|
+
return if node.arguments.one? || !node.arguments[1]&.hash_type?
|
|
24
|
+
|
|
25
|
+
range = node.first_argument.source_range.end.join(node.last_argument.source_range.end)
|
|
26
|
+
|
|
27
|
+
add_offense(range) do |corrector|
|
|
28
|
+
corrector.remove(range)
|
|
29
|
+
end
|
|
30
|
+
end
|
|
31
|
+
end
|
|
32
|
+
end
|
|
33
|
+
end
|
|
34
|
+
end
|
|
@@ -12,6 +12,7 @@ require_relative 'internal_affairs/location_line_equality_comparison'
|
|
|
12
12
|
require_relative 'internal_affairs/method_name_end_with'
|
|
13
13
|
require_relative 'internal_affairs/method_name_equal'
|
|
14
14
|
require_relative 'internal_affairs/node_destructuring'
|
|
15
|
+
require_relative 'internal_affairs/node_first_or_last_argument'
|
|
15
16
|
require_relative 'internal_affairs/node_matcher_directive'
|
|
16
17
|
require_relative 'internal_affairs/node_type_predicate'
|
|
17
18
|
require_relative 'internal_affairs/numblock_handler'
|
|
@@ -19,6 +20,7 @@ require_relative 'internal_affairs/offense_location_keyword'
|
|
|
19
20
|
require_relative 'internal_affairs/processed_source_buffer_name'
|
|
20
21
|
require_relative 'internal_affairs/redundant_context_config_parameter'
|
|
21
22
|
require_relative 'internal_affairs/redundant_described_class_as_subject'
|
|
23
|
+
require_relative 'internal_affairs/redundant_expect_offense_arguments'
|
|
22
24
|
require_relative 'internal_affairs/redundant_let_rubocop_config_new'
|
|
23
25
|
require_relative 'internal_affairs/redundant_location_argument'
|
|
24
26
|
require_relative 'internal_affairs/redundant_message_argument'
|
|
@@ -121,7 +121,7 @@ module RuboCop
|
|
|
121
121
|
return if case_node.single_line?
|
|
122
122
|
return if enforced_style_end? && end_and_last_conditional_same_line?(case_node)
|
|
123
123
|
|
|
124
|
-
case_node.
|
|
124
|
+
case_node.when_branches.each { |when_node| check_when(when_node, 'when') }
|
|
125
125
|
end
|
|
126
126
|
|
|
127
127
|
def on_case_match(case_match_node)
|
|
@@ -106,7 +106,9 @@ module RuboCop
|
|
|
106
106
|
end
|
|
107
107
|
|
|
108
108
|
def concat_consecutive_comments(comments)
|
|
109
|
-
consecutive_comments = comments.chunk_while
|
|
109
|
+
consecutive_comments = comments.chunk_while do |i, j|
|
|
110
|
+
i.loc.line.succ == j.loc.line && i.loc.column == j.loc.column
|
|
111
|
+
end
|
|
110
112
|
|
|
111
113
|
consecutive_comments.map do |chunk|
|
|
112
114
|
joined_text = chunk.map { |c| comment_text(c) }.join
|
|
@@ -27,9 +27,9 @@ module RuboCop
|
|
|
27
27
|
MSG = 'Add an empty line after magic comments.'
|
|
28
28
|
|
|
29
29
|
def on_new_investigation
|
|
30
|
-
return unless processed_source
|
|
31
|
-
|
|
32
|
-
return if
|
|
30
|
+
return unless (last_magic_comment = last_magic_comment(processed_source))
|
|
31
|
+
return unless (next_line = processed_source[last_magic_comment.loc.line])
|
|
32
|
+
return if next_line.strip.empty?
|
|
33
33
|
|
|
34
34
|
offending_range = offending_range(last_magic_comment)
|
|
35
35
|
|
|
@@ -46,18 +46,25 @@ module RuboCop
|
|
|
46
46
|
|
|
47
47
|
# Find the last magic comment in the source file.
|
|
48
48
|
#
|
|
49
|
-
# Take all comments that precede the first line of code
|
|
49
|
+
# Take all comments that precede the first line of code (or just take
|
|
50
|
+
# them all in the case when there is no code), select the
|
|
50
51
|
# magic comments, and return the last magic comment in the file.
|
|
51
52
|
#
|
|
52
53
|
# @return [Parser::Source::Comment] if magic comments exist before code
|
|
53
54
|
# @return [nil] otherwise
|
|
54
55
|
def last_magic_comment(source)
|
|
55
|
-
source
|
|
56
|
-
.comments
|
|
57
|
-
.take_while { |comment| comment.loc.line < source.ast.loc.line }
|
|
56
|
+
comments_before_code(source)
|
|
58
57
|
.reverse
|
|
59
58
|
.find { |comment| MagicComment.parse(comment.text).any? }
|
|
60
59
|
end
|
|
60
|
+
|
|
61
|
+
def comments_before_code(source)
|
|
62
|
+
if source.ast
|
|
63
|
+
source.comments.take_while { |comment| comment.loc.line < source.ast.loc.line }
|
|
64
|
+
else
|
|
65
|
+
source.comments
|
|
66
|
+
end
|
|
67
|
+
end
|
|
61
68
|
end
|
|
62
69
|
end
|
|
63
70
|
end
|
|
@@ -20,7 +20,9 @@ module RuboCop
|
|
|
20
20
|
# This `Layout/EndAlignment` cop aligns with keywords (e.g. `if`, `while`, `case`)
|
|
21
21
|
# by default. On the other hand, `Layout/BeginEndAlignment` cop aligns with
|
|
22
22
|
# `EnforcedStyleAlignWith: start_of_line` by default due to `||= begin` tends
|
|
23
|
-
# to align with the start of the line.
|
|
23
|
+
# to align with the start of the line. `Layout/DefEndAlignment` cop also aligns with
|
|
24
|
+
# `EnforcedStyleAlignWith: start_of_line` by default.
|
|
25
|
+
# These style can be configured by each cop.
|
|
24
26
|
#
|
|
25
27
|
# @example EnforcedStyleAlignWith: keyword (default)
|
|
26
28
|
# # bad
|
|
@@ -83,7 +85,11 @@ module RuboCop
|
|
|
83
85
|
end
|
|
84
86
|
|
|
85
87
|
def on_sclass(node)
|
|
86
|
-
|
|
88
|
+
if node.parent&.assignment?
|
|
89
|
+
check_asgn_alignment(node.parent, node)
|
|
90
|
+
else
|
|
91
|
+
check_other_alignment(node)
|
|
92
|
+
end
|
|
87
93
|
end
|
|
88
94
|
|
|
89
95
|
def on_module(node)
|
|
@@ -163,7 +169,13 @@ module RuboCop
|
|
|
163
169
|
when :keyword
|
|
164
170
|
node
|
|
165
171
|
when :variable
|
|
166
|
-
alignment_node_for_variable_style(node)
|
|
172
|
+
align_to = alignment_node_for_variable_style(node)
|
|
173
|
+
|
|
174
|
+
while (parent = align_to.parent) && parent.send_type? && same_line?(align_to, parent)
|
|
175
|
+
align_to = parent
|
|
176
|
+
end
|
|
177
|
+
|
|
178
|
+
align_to
|
|
167
179
|
else
|
|
168
180
|
start_line_range(node)
|
|
169
181
|
end
|