rubocop 1.71.1 → 1.92.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 +23 -19
- data/config/default.yml +885 -168
- data/config/internal_affairs.yml +20 -0
- data/config/obsoletion.yml +47 -4
- data/exe/rubocop +2 -9
- data/lib/rubocop/cache_config.rb +29 -0
- data/lib/rubocop/cached_data.rb +50 -5
- data/lib/rubocop/changed_files.rb +134 -0
- data/lib/rubocop/cli/command/auto_generate_config.rb +36 -4
- data/lib/rubocop/cli/command/cop_names.rb +57 -0
- data/lib/rubocop/cli/command/execute_runner.rb +54 -3
- data/lib/rubocop/cli/command/explain.rb +34 -0
- data/lib/rubocop/cli/command/list_enabled_cops_for.rb +40 -0
- data/lib/rubocop/cli/command/lsp.rb +1 -1
- data/lib/rubocop/cli/command/mcp.rb +19 -0
- data/lib/rubocop/cli/command/show_cops.rb +8 -2
- data/lib/rubocop/cli/command/show_docs_url.rb +8 -10
- data/lib/rubocop/cli/command/suggest_extensions.rb +8 -2
- data/lib/rubocop/cli.rb +59 -17
- data/lib/rubocop/comment_config/directive_range.rb +34 -0
- data/lib/rubocop/comment_config/disable_next.rb +143 -0
- data/lib/rubocop/comment_config/push_pop.rb +55 -0
- data/lib/rubocop/comment_config.rb +98 -45
- data/lib/rubocop/config.rb +137 -19
- data/lib/rubocop/config_finder.rb +1 -1
- data/lib/rubocop/config_loader.rb +75 -49
- data/lib/rubocop/config_loader_resolver.rb +124 -33
- data/lib/rubocop/config_obsoletion/cop_rule.rb +2 -1
- data/lib/rubocop/config_obsoletion/extracted_cop.rb +6 -3
- data/lib/rubocop/config_obsoletion/removed_cop.rb +9 -1
- data/lib/rubocop/config_obsoletion/renamed_cop.rb +18 -3
- data/lib/rubocop/config_obsoletion.rb +47 -3
- data/lib/rubocop/config_store.rb +7 -2
- data/lib/rubocop/config_validator.rb +75 -12
- data/lib/rubocop/cop/autocorrect_logic.rb +43 -17
- data/lib/rubocop/cop/badge.rb +9 -1
- data/lib/rubocop/cop/base.rb +128 -35
- data/lib/rubocop/cop/bundler/gem_comment.rb +5 -4
- data/lib/rubocop/cop/bundler/gem_version.rb +28 -28
- data/lib/rubocop/cop/bundler/ordered_gems.rb +2 -11
- data/lib/rubocop/cop/bundler.rb +19 -0
- data/lib/rubocop/cop/commissioner.rb +13 -11
- data/lib/rubocop/cop/cop_documentation.rb +81 -0
- data/lib/rubocop/cop/cop_explanation.rb +140 -0
- data/lib/rubocop/cop/corrector.rb +4 -4
- data/lib/rubocop/cop/correctors/alignment_corrector.rb +92 -11
- data/lib/rubocop/cop/correctors/condition_corrector.rb +1 -1
- data/lib/rubocop/cop/correctors/each_to_for_corrector.rb +22 -7
- data/lib/rubocop/cop/correctors/empty_line_corrector.rb +1 -1
- data/lib/rubocop/cop/correctors/for_to_each_corrector.rb +7 -2
- data/lib/rubocop/cop/correctors/lambda_literal_to_method_corrector.rb +29 -2
- data/lib/rubocop/cop/correctors/multiline_literal_brace_corrector.rb +1 -5
- data/lib/rubocop/cop/correctors/ordered_gem_corrector.rb +8 -1
- data/lib/rubocop/cop/correctors/parentheses_corrector.rb +73 -2
- data/lib/rubocop/cop/correctors/percent_literal_corrector.rb +2 -2
- data/lib/rubocop/cop/correctors.rb +28 -0
- data/lib/rubocop/cop/documentation.rb +3 -4
- data/lib/rubocop/cop/exclude_limit.rb +31 -5
- data/lib/rubocop/cop/gemspec/attribute_assignment.rb +91 -0
- data/lib/rubocop/cop/gemspec/dependency_version.rb +0 -6
- data/lib/rubocop/cop/gemspec/development_dependencies.rb +1 -1
- data/lib/rubocop/cop/gemspec/duplicated_assignment.rb +49 -17
- data/lib/rubocop/cop/gemspec/ordered_dependencies.rb +2 -9
- data/lib/rubocop/cop/gemspec/require_mfa.rb +22 -5
- data/lib/rubocop/cop/gemspec/ruby_version_globals_usage.rb +12 -7
- data/lib/rubocop/cop/gemspec.rb +22 -0
- data/lib/rubocop/cop/generator/registration_injector.rb +188 -0
- data/lib/rubocop/cop/generator.rb +5 -1
- data/lib/rubocop/cop/internal_affairs/example_description.rb +9 -5
- data/lib/rubocop/cop/internal_affairs/example_heredoc_delimiter.rb +8 -8
- data/lib/rubocop/cop/internal_affairs/itblock_handler.rb +69 -0
- data/lib/rubocop/cop/internal_affairs/location_exists.rb +142 -0
- data/lib/rubocop/cop/internal_affairs/location_line_equality_comparison.rb +1 -0
- data/lib/rubocop/cop/internal_affairs/node_matcher_directive.rb +16 -20
- data/lib/rubocop/cop/internal_affairs/node_pattern_groups/ast_processor.rb +1 -1
- data/lib/rubocop/cop/internal_affairs/node_pattern_groups/ast_walker.rb +1 -2
- data/lib/rubocop/cop/internal_affairs/node_pattern_groups.rb +6 -2
- data/lib/rubocop/cop/internal_affairs/node_type_group.rb +85 -0
- data/lib/rubocop/cop/internal_affairs/on_send_without_on_csend.rb +2 -2
- data/lib/rubocop/cop/internal_affairs/plugin.rb +33 -0
- data/lib/rubocop/cop/internal_affairs/redundant_context_config_parameter.rb +1 -7
- data/lib/rubocop/cop/internal_affairs/redundant_described_class_as_subject.rb +6 -5
- data/lib/rubocop/cop/internal_affairs/redundant_let_rubocop_config_new.rb +5 -3
- data/lib/rubocop/cop/internal_affairs/style_detected_api_use.rb +1 -7
- data/lib/rubocop/cop/internal_affairs/undefined_config.rb +13 -2
- data/lib/rubocop/cop/internal_affairs/useless_message_assertion.rb +4 -4
- data/lib/rubocop/cop/internal_affairs/useless_restrict_on_send.rb +1 -1
- data/lib/rubocop/cop/internal_affairs.rb +3 -16
- data/lib/rubocop/cop/layout/argument_alignment.rb +4 -2
- data/lib/rubocop/cop/layout/array_alignment.rb +1 -1
- data/lib/rubocop/cop/layout/begin_end_alignment.rb +1 -1
- data/lib/rubocop/cop/layout/block_alignment.rb +86 -4
- data/lib/rubocop/cop/layout/block_end_newline.rb +1 -0
- data/lib/rubocop/cop/layout/case_indentation.rb +28 -10
- data/lib/rubocop/cop/layout/class_structure.rb +172 -36
- data/lib/rubocop/cop/layout/closing_parenthesis_indentation.rb +5 -5
- data/lib/rubocop/cop/layout/comment_indentation.rb +17 -7
- data/lib/rubocop/cop/layout/condition_position.rb +13 -3
- data/lib/rubocop/cop/layout/def_end_alignment.rb +5 -1
- data/lib/rubocop/cop/layout/dot_position.rb +2 -2
- data/lib/rubocop/cop/layout/else_alignment.rb +3 -15
- data/lib/rubocop/cop/layout/empty_comment.rb +8 -10
- data/lib/rubocop/cop/layout/empty_line_after_guard_clause.rb +27 -9
- data/lib/rubocop/cop/layout/empty_line_after_magic_comment.rb +63 -5
- data/lib/rubocop/cop/layout/empty_line_after_multiline_condition.rb +14 -5
- data/lib/rubocop/cop/layout/empty_line_between_defs.rb +46 -21
- data/lib/rubocop/cop/layout/empty_lines.rb +5 -2
- data/lib/rubocop/cop/layout/empty_lines_after_module_inclusion.rb +101 -0
- data/lib/rubocop/cop/layout/empty_lines_around_access_modifier.rb +34 -4
- data/lib/rubocop/cop/layout/empty_lines_around_arguments.rb +8 -29
- data/lib/rubocop/cop/layout/empty_lines_around_attribute_accessor.rb +2 -0
- data/lib/rubocop/cop/layout/empty_lines_around_block_body.rb +14 -3
- data/lib/rubocop/cop/layout/empty_lines_around_class_body.rb +17 -3
- data/lib/rubocop/cop/layout/empty_lines_around_exception_handling_keywords.rb +23 -1
- data/lib/rubocop/cop/layout/empty_lines_around_method_body.rb +22 -2
- data/lib/rubocop/cop/layout/empty_lines_around_module_body.rb +16 -2
- data/lib/rubocop/cop/layout/end_alignment.rb +20 -8
- data/lib/rubocop/cop/layout/extra_spacing.rb +109 -3
- data/lib/rubocop/cop/layout/first_argument_indentation.rb +57 -3
- data/lib/rubocop/cop/layout/first_array_element_indentation.rb +18 -5
- data/lib/rubocop/cop/layout/first_array_element_line_break.rb +26 -0
- data/lib/rubocop/cop/layout/first_hash_element_indentation.rb +25 -18
- data/lib/rubocop/cop/layout/first_hash_element_line_break.rb +25 -25
- data/lib/rubocop/cop/layout/first_method_argument_line_break.rb +6 -0
- data/lib/rubocop/cop/layout/first_method_parameter_line_break.rb +4 -0
- data/lib/rubocop/cop/layout/first_parameter_indentation.rb +11 -0
- data/lib/rubocop/cop/layout/hash_alignment.rb +20 -18
- data/lib/rubocop/cop/layout/heredoc_argument_closing_parenthesis.rb +5 -3
- data/lib/rubocop/cop/layout/heredoc_indentation.rb +48 -3
- data/lib/rubocop/cop/layout/indentation_style.rb +5 -2
- data/lib/rubocop/cop/layout/indentation_width.rb +159 -12
- data/lib/rubocop/cop/layout/leading_comment_space.rb +40 -1
- data/lib/rubocop/cop/layout/line_continuation_spacing.rb +10 -4
- data/lib/rubocop/cop/layout/line_end_string_concatenation_indentation.rb +25 -9
- data/lib/rubocop/cop/layout/line_length.rb +201 -30
- data/lib/rubocop/cop/layout/multiline_array_brace_layout.rb +69 -57
- data/lib/rubocop/cop/layout/multiline_assignment_layout.rb +8 -2
- data/lib/rubocop/cop/layout/multiline_block_layout.rb +11 -1
- data/lib/rubocop/cop/layout/multiline_hash_brace_layout.rb +63 -56
- data/lib/rubocop/cop/layout/multiline_method_call_brace_layout.rb +7 -1
- data/lib/rubocop/cop/layout/multiline_method_call_indentation.rb +259 -40
- data/lib/rubocop/cop/layout/multiline_method_definition_brace_layout.rb +4 -0
- data/lib/rubocop/cop/layout/multiline_method_parameter_line_breaks.rb +1 -0
- data/lib/rubocop/cop/layout/multiline_operation_indentation.rb +9 -5
- data/lib/rubocop/cop/layout/parameter_alignment.rb +1 -1
- data/lib/rubocop/cop/layout/redundant_line_break.rb +111 -7
- data/lib/rubocop/cop/layout/rescue_ensure_alignment.rb +29 -9
- data/lib/rubocop/cop/layout/single_line_block_chain.rb +10 -2
- data/lib/rubocop/cop/layout/space_after_comma.rb +2 -10
- data/lib/rubocop/cop/layout/space_after_not.rb +5 -0
- data/lib/rubocop/cop/layout/space_after_semicolon.rb +11 -1
- data/lib/rubocop/cop/layout/space_around_block_parameters.rb +10 -4
- data/lib/rubocop/cop/layout/space_around_keyword.rb +20 -3
- data/lib/rubocop/cop/layout/space_around_method_call_operator.rb +1 -1
- data/lib/rubocop/cop/layout/space_around_operators.rb +30 -4
- data/lib/rubocop/cop/layout/space_before_block_braces.rb +5 -1
- data/lib/rubocop/cop/layout/space_before_brackets.rb +6 -39
- data/lib/rubocop/cop/layout/space_in_lambda_literal.rb +9 -8
- data/lib/rubocop/cop/layout/space_inside_array_literal_brackets.rb +55 -36
- data/lib/rubocop/cop/layout/space_inside_block_braces.rb +32 -8
- data/lib/rubocop/cop/layout/space_inside_hash_literal_braces.rb +3 -0
- data/lib/rubocop/cop/layout/trailing_whitespace.rb +1 -1
- data/lib/rubocop/cop/layout.rb +114 -0
- data/lib/rubocop/cop/lazy_loader.rb +41 -0
- data/lib/rubocop/cop/lint/ambiguous_assignment.rb +9 -17
- data/lib/rubocop/cop/lint/ambiguous_block_association.rb +72 -1
- data/lib/rubocop/cop/lint/ambiguous_operator.rb +1 -1
- data/lib/rubocop/cop/lint/ambiguous_operator_precedence.rb +3 -11
- data/lib/rubocop/cop/lint/ambiguous_range.rb +6 -2
- data/lib/rubocop/cop/lint/argument_mismatch.rb +99 -0
- data/lib/rubocop/cop/lint/array_literal_in_regexp.rb +2 -3
- data/lib/rubocop/cop/lint/assignment_in_condition.rb +15 -1
- data/lib/rubocop/cop/lint/boolean_symbol.rb +1 -1
- data/lib/rubocop/cop/lint/circular_argument_reference.rb +47 -8
- data/lib/rubocop/cop/lint/constant_overwritten_in_rescue.rb +4 -3
- data/lib/rubocop/cop/lint/constant_reassignment.rb +94 -15
- data/lib/rubocop/cop/lint/constant_resolution.rb +31 -6
- data/lib/rubocop/cop/lint/cop_directive_syntax.rb +240 -0
- data/lib/rubocop/cop/lint/data_define_override.rb +63 -0
- data/lib/rubocop/cop/lint/debugger.rb +13 -4
- data/lib/rubocop/cop/lint/deprecated_class_methods.rb +1 -1
- data/lib/rubocop/cop/lint/deprecated_constants.rb +2 -8
- data/lib/rubocop/cop/lint/deprecated_open_ssl_constant.rb +5 -2
- data/lib/rubocop/cop/lint/deprecated_reference.rb +194 -0
- data/lib/rubocop/cop/lint/duplicate_match_pattern.rb +4 -4
- data/lib/rubocop/cop/lint/duplicate_methods.rb +506 -41
- data/lib/rubocop/cop/lint/duplicate_regexp_character_class_element.rb +5 -42
- data/lib/rubocop/cop/lint/else_layout.rb +19 -0
- data/lib/rubocop/cop/lint/empty_block.rb +4 -4
- data/lib/rubocop/cop/lint/empty_conditional_body.rb +22 -65
- data/lib/rubocop/cop/lint/empty_expression.rb +0 -2
- data/lib/rubocop/cop/lint/empty_in_pattern.rb +8 -1
- data/lib/rubocop/cop/lint/empty_interpolation.rb +14 -1
- data/lib/rubocop/cop/lint/empty_when.rb +8 -1
- data/lib/rubocop/cop/lint/ensure_return.rb +19 -1
- data/lib/rubocop/cop/lint/erb_new_arguments.rb +4 -8
- data/lib/rubocop/cop/lint/float_comparison.rb +33 -10
- data/lib/rubocop/cop/lint/format_parameter_mismatch.rb +1 -1
- data/lib/rubocop/cop/lint/identity_comparison.rb +19 -15
- data/lib/rubocop/cop/lint/implicit_string_concatenation.rb +1 -2
- data/lib/rubocop/cop/lint/incompatible_io_select_with_fiber_scheduler.rb +5 -1
- data/lib/rubocop/cop/lint/ineffective_access_modifier.rb +1 -2
- data/lib/rubocop/cop/lint/inherit_exception.rb +53 -7
- data/lib/rubocop/cop/lint/interpolation_check.rb +25 -6
- data/lib/rubocop/cop/lint/lambda_without_literal_block.rb +1 -1
- data/lib/rubocop/cop/lint/literal_as_condition.rb +152 -11
- data/lib/rubocop/cop/lint/literal_assignment_in_condition.rb +11 -1
- data/lib/rubocop/cop/lint/literal_in_interpolation.rb +75 -37
- data/lib/rubocop/cop/lint/loop.rb +24 -2
- data/lib/rubocop/cop/lint/misplaced_magic_comment.rb +245 -0
- data/lib/rubocop/cop/lint/missing_cop_enable_directive.rb +60 -23
- data/lib/rubocop/cop/lint/missing_super.rb +31 -1
- data/lib/rubocop/cop/lint/mixed_case_range.rb +2 -2
- data/lib/rubocop/cop/lint/multiple_comparison.rb +2 -2
- data/lib/rubocop/cop/lint/name_typo.rb +270 -0
- data/lib/rubocop/cop/lint/nested_method_definition.rb +2 -2
- data/lib/rubocop/cop/lint/next_without_accumulator.rb +2 -0
- data/lib/rubocop/cop/lint/no_return_in_begin_end_blocks.rb +20 -0
- data/lib/rubocop/cop/lint/non_deterministic_require_order.rb +4 -2
- data/lib/rubocop/cop/lint/non_local_exit_from_iterator.rb +4 -4
- data/lib/rubocop/cop/lint/number_conversion.rb +20 -11
- data/lib/rubocop/cop/lint/numbered_parameter_assignment.rb +1 -1
- data/lib/rubocop/cop/lint/numeric_operation_with_constant_result.rb +11 -0
- data/lib/rubocop/cop/lint/or_assignment_to_constant.rb +1 -1
- data/lib/rubocop/cop/lint/ordered_magic_comments.rb +7 -7
- data/lib/rubocop/cop/lint/out_of_range_regexp_ref.rb +15 -4
- data/lib/rubocop/cop/lint/parentheses_as_grouped_expression.rb +20 -14
- data/lib/rubocop/cop/lint/raise_exception.rb +30 -11
- data/lib/rubocop/cop/lint/rand_one.rb +1 -1
- data/lib/rubocop/cop/lint/redundant_cop_disable_directive.rb +160 -39
- data/lib/rubocop/cop/lint/redundant_cop_enable_directive.rb +53 -19
- data/lib/rubocop/cop/lint/redundant_dir_glob_sort.rb +28 -6
- data/lib/rubocop/cop/lint/redundant_regexp_quantifiers.rb +1 -1
- data/lib/rubocop/cop/lint/redundant_require_statement.rb +5 -25
- data/lib/rubocop/cop/lint/redundant_safe_navigation.rb +134 -12
- data/lib/rubocop/cop/lint/redundant_splat_expansion.rb +13 -4
- data/lib/rubocop/cop/lint/redundant_type_conversion.rb +267 -0
- data/lib/rubocop/cop/lint/redundant_with_index.rb +5 -3
- data/lib/rubocop/cop/lint/redundant_with_object.rb +8 -0
- data/lib/rubocop/cop/lint/refinement_import_methods.rb +8 -1
- data/lib/rubocop/cop/lint/regexp_as_condition.rb +9 -1
- data/lib/rubocop/cop/lint/require_parentheses.rb +13 -4
- data/lib/rubocop/cop/lint/require_range_parentheses.rb +3 -2
- data/lib/rubocop/cop/lint/require_relative_self_path.rb +7 -5
- data/lib/rubocop/cop/lint/rescue_exception.rb +1 -4
- data/lib/rubocop/cop/lint/rescue_type.rb +2 -2
- data/lib/rubocop/cop/lint/return_in_void_context.rb +9 -11
- data/lib/rubocop/cop/lint/safe_navigation_chain.rb +28 -4
- data/lib/rubocop/cop/lint/safe_navigation_consistency.rb +9 -5
- data/lib/rubocop/cop/lint/safe_navigation_with_empty.rb +1 -1
- data/lib/rubocop/cop/lint/script_permission.rb +5 -1
- data/lib/rubocop/cop/lint/self_assignment.rb +63 -6
- data/lib/rubocop/cop/lint/send_with_mixin_argument.rb +1 -1
- data/lib/rubocop/cop/lint/shadowed_argument.rb +7 -7
- data/lib/rubocop/cop/lint/shadowed_exception.rb +1 -1
- data/lib/rubocop/cop/lint/shadowing_outer_local_variable.rb +27 -1
- data/lib/rubocop/cop/lint/shared_mutable_default.rb +14 -1
- data/lib/rubocop/cop/lint/struct_new_override.rb +17 -1
- data/lib/rubocop/cop/lint/super_argument_mismatch.rb +179 -0
- data/lib/rubocop/cop/lint/suppressed_exception.rb +1 -1
- data/lib/rubocop/cop/lint/suppressed_exception_in_number_conversion.rb +122 -0
- data/lib/rubocop/cop/lint/symbol_conversion.rb +21 -4
- data/lib/rubocop/cop/lint/syntax.rb +25 -1
- data/lib/rubocop/cop/lint/to_enum_arguments.rb +73 -5
- data/lib/rubocop/cop/lint/to_json.rb +20 -17
- data/lib/rubocop/cop/lint/top_level_return_with_argument.rb +1 -1
- data/lib/rubocop/cop/lint/trailing_comma_in_attribute_declaration.rb +5 -1
- data/lib/rubocop/cop/lint/unescaped_bracket_in_regexp.rb +54 -11
- data/lib/rubocop/cop/lint/unexpected_block_arity.rb +2 -0
- data/lib/rubocop/cop/lint/unmodified_reduce_accumulator.rb +2 -1
- data/lib/rubocop/cop/lint/unreachable_code.rb +16 -9
- data/lib/rubocop/cop/lint/unreachable_loop.rb +5 -5
- data/lib/rubocop/cop/lint/unreachable_pattern_branch.rb +113 -0
- data/lib/rubocop/cop/lint/unused_method_argument.rb +10 -0
- data/lib/rubocop/cop/lint/unused_private_method.rb +234 -0
- data/lib/rubocop/cop/lint/uri_escape_unescape.rb +2 -0
- data/lib/rubocop/cop/lint/useless_access_modifier.rb +31 -6
- data/lib/rubocop/cop/lint/useless_assignment.rb +63 -27
- data/lib/rubocop/cop/lint/useless_constant_scoping.rb +107 -0
- data/lib/rubocop/cop/lint/useless_default_value_argument.rb +92 -0
- data/lib/rubocop/cop/lint/useless_method_definition.rb +1 -1
- data/lib/rubocop/cop/lint/useless_numeric_operation.rb +11 -10
- data/lib/rubocop/cop/lint/useless_or.rb +111 -0
- data/lib/rubocop/cop/lint/useless_rescue.rb +2 -3
- data/lib/rubocop/cop/lint/useless_ruby2_keywords.rb +13 -7
- data/lib/rubocop/cop/lint/useless_setter_call.rb +4 -1
- data/lib/rubocop/cop/lint/useless_times.rb +22 -1
- data/lib/rubocop/cop/lint/utils/nil_receiver_checker.rb +201 -0
- data/lib/rubocop/cop/lint/void.rb +68 -22
- data/lib/rubocop/cop/lint.rb +179 -0
- data/lib/rubocop/cop/message_annotator.rb +7 -3
- data/lib/rubocop/cop/metrics/abc_size.rb +1 -1
- data/lib/rubocop/cop/metrics/block_length.rb +2 -1
- data/lib/rubocop/cop/metrics/block_nesting.rb +23 -0
- data/lib/rubocop/cop/metrics/class_length.rb +4 -2
- data/lib/rubocop/cop/metrics/collection_literal_length.rb +1 -1
- data/lib/rubocop/cop/metrics/cyclomatic_complexity.rb +0 -4
- data/lib/rubocop/cop/metrics/method_length.rb +3 -2
- data/lib/rubocop/cop/metrics/module_length.rb +4 -2
- data/lib/rubocop/cop/metrics/perceived_complexity.rb +37 -7
- data/lib/rubocop/cop/metrics/utils/abc_size_calculator.rb +4 -3
- data/lib/rubocop/cop/metrics/utils/code_length_calculator.rb +2 -2
- data/lib/rubocop/cop/metrics/utils/iterating_block.rb +1 -1
- data/lib/rubocop/cop/metrics/utils/repeated_attribute_discount.rb +7 -7
- data/lib/rubocop/cop/metrics.rb +31 -0
- data/lib/rubocop/cop/migration/department_name.rb +11 -5
- data/lib/rubocop/cop/migration.rb +13 -0
- data/lib/rubocop/cop/mixin/alignment.rb +7 -3
- data/lib/rubocop/cop/mixin/allowed_methods.rb +5 -5
- data/lib/rubocop/cop/mixin/allowed_pattern.rb +9 -5
- data/lib/rubocop/cop/mixin/annotation_comment.rb +1 -1
- data/lib/rubocop/cop/mixin/check_line_breakable.rb +44 -23
- data/lib/rubocop/cop/mixin/check_single_line_suitability.rb +10 -8
- data/lib/rubocop/cop/mixin/code_length.rb +10 -2
- data/lib/rubocop/cop/mixin/comments_help.rb +2 -3
- data/lib/rubocop/cop/mixin/configurable_enforced_style.rb +1 -2
- data/lib/rubocop/cop/mixin/configurable_max.rb +6 -5
- data/lib/rubocop/cop/mixin/def_node.rb +1 -1
- data/lib/rubocop/cop/mixin/empty_lines_around_body.rb +13 -2
- data/lib/rubocop/cop/mixin/end_keyword_alignment.rb +1 -7
- data/lib/rubocop/cop/mixin/endless_method_body_help.rb +69 -0
- data/lib/rubocop/cop/mixin/endless_method_rewriter.rb +13 -5
- data/lib/rubocop/cop/mixin/forbidden_identifiers.rb +20 -0
- data/lib/rubocop/cop/mixin/forbidden_pattern.rb +20 -0
- data/lib/rubocop/cop/mixin/frozen_string_literal.rb +1 -2
- data/lib/rubocop/cop/mixin/gemspec_help.rb +22 -0
- data/lib/rubocop/cop/mixin/hash_alignment_styles.rb +59 -17
- data/lib/rubocop/cop/mixin/hash_shorthand_syntax.rb +52 -25
- data/lib/rubocop/cop/mixin/hash_subset.rb +28 -6
- data/lib/rubocop/cop/mixin/hash_transform_method/autocorrection.rb +63 -0
- data/lib/rubocop/cop/mixin/hash_transform_method.rb +32 -78
- data/lib/rubocop/cop/mixin/indexed_method_arity.rb +94 -0
- data/lib/rubocop/cop/mixin/line_length_help.rb +52 -11
- data/lib/rubocop/cop/mixin/method_complexity.rb +2 -1
- data/lib/rubocop/cop/mixin/min_branches_count.rb +3 -1
- data/lib/rubocop/cop/mixin/multiline_element_line_breaks.rb +11 -1
- data/lib/rubocop/cop/mixin/multiline_expression_indentation.rb +3 -1
- data/lib/rubocop/cop/mixin/multiline_literal_brace_layout.rb +10 -1
- data/lib/rubocop/cop/mixin/ordered_gem_node.rb +2 -2
- data/lib/rubocop/cop/mixin/pattern_matching_help.rb +35 -0
- data/lib/rubocop/cop/mixin/percent_literal.rb +1 -1
- data/lib/rubocop/cop/mixin/preceding_following_alignment.rb +79 -8
- data/lib/rubocop/cop/mixin/project_index_help.rb +203 -0
- data/lib/rubocop/cop/mixin/range_help.rb +16 -5
- data/lib/rubocop/cop/mixin/reparsed_equivalence.rb +181 -0
- data/lib/rubocop/cop/mixin/space_after_punctuation.rb +5 -4
- data/lib/rubocop/cop/mixin/statement_modifier.rb +66 -10
- data/lib/rubocop/cop/mixin/string_help.rb +1 -1
- data/lib/rubocop/cop/mixin/target_ruby_version.rb +1 -1
- data/lib/rubocop/cop/mixin/trailing_comma.rb +23 -6
- data/lib/rubocop/cop/mixin.rb +93 -0
- data/lib/rubocop/cop/naming/accessor_method_name.rb +8 -0
- data/lib/rubocop/cop/naming/binary_operator_parameter_name.rb +17 -1
- data/lib/rubocop/cop/naming/block_forwarding.rb +7 -4
- data/lib/rubocop/cop/naming/block_parameter_name.rb +1 -1
- data/lib/rubocop/cop/naming/file_name.rb +6 -5
- data/lib/rubocop/cop/naming/heredoc_delimiter_case.rb +9 -2
- data/lib/rubocop/cop/naming/heredoc_delimiter_naming.rb +5 -3
- data/lib/rubocop/cop/naming/inclusive_language.rb +8 -2
- data/lib/rubocop/cop/naming/memoized_instance_variable_name.rb +13 -6
- data/lib/rubocop/cop/naming/method_name.rb +190 -15
- data/lib/rubocop/cop/naming/predicate_method.rb +330 -0
- data/lib/rubocop/cop/naming/{predicate_name.rb → predicate_prefix.rb} +65 -8
- data/lib/rubocop/cop/naming/rescued_exceptions_variable_name.rb +11 -6
- data/lib/rubocop/cop/naming/variable_name.rb +51 -6
- data/lib/rubocop/cop/naming/variable_number.rb +3 -1
- data/lib/rubocop/cop/naming.rb +31 -0
- data/lib/rubocop/cop/offense.rb +108 -9
- data/lib/rubocop/cop/registry.rb +234 -65
- data/lib/rubocop/cop/security/eval.rb +17 -3
- data/lib/rubocop/cop/security/io_methods.rb +2 -2
- data/lib/rubocop/cop/security/json_load.rb +45 -11
- data/lib/rubocop/cop/security/marshal_load.rb +1 -1
- data/lib/rubocop/cop/security/open.rb +1 -0
- data/lib/rubocop/cop/security.rb +19 -0
- data/lib/rubocop/cop/severity.rb +12 -0
- data/lib/rubocop/cop/style/access_modifier_declarations.rb +54 -13
- data/lib/rubocop/cop/style/accessor_grouping.rb +47 -10
- data/lib/rubocop/cop/style/alias.rb +33 -8
- data/lib/rubocop/cop/style/ambiguous_endless_method_definition.rb +4 -3
- data/lib/rubocop/cop/style/and_or.rb +6 -1
- data/lib/rubocop/cop/style/arguments_forwarding.rb +52 -37
- data/lib/rubocop/cop/style/array_first_last.rb +13 -3
- data/lib/rubocop/cop/style/array_intersect.rb +136 -38
- data/lib/rubocop/cop/style/array_intersect_with_single_element.rb +50 -0
- data/lib/rubocop/cop/style/array_join.rb +4 -2
- data/lib/rubocop/cop/style/ascii_comments.rb +6 -3
- data/lib/rubocop/cop/style/attr.rb +8 -6
- data/lib/rubocop/cop/style/bare_percent_literals.rb +4 -3
- data/lib/rubocop/cop/style/begin_block.rb +3 -1
- data/lib/rubocop/cop/style/bitwise_predicate.rb +13 -5
- data/lib/rubocop/cop/style/block_delimiters.rb +71 -40
- data/lib/rubocop/cop/style/case_equality.rb +29 -15
- data/lib/rubocop/cop/style/case_like_if.rb +12 -11
- data/lib/rubocop/cop/style/character_literal.rb +2 -2
- data/lib/rubocop/cop/style/class_and_module_children.rb +179 -27
- data/lib/rubocop/cop/style/class_equality_comparison.rb +22 -14
- data/lib/rubocop/cop/style/class_methods_definitions.rb +19 -5
- data/lib/rubocop/cop/style/collection_compact.rb +37 -17
- data/lib/rubocop/cop/style/collection_methods.rb +1 -0
- data/lib/rubocop/cop/style/collection_querying.rb +167 -0
- data/lib/rubocop/cop/style/colon_method_call.rb +16 -7
- data/lib/rubocop/cop/style/combinable_loops.rb +88 -9
- data/lib/rubocop/cop/style/command_literal.rb +1 -1
- data/lib/rubocop/cop/style/commented_keyword.rb +12 -5
- data/lib/rubocop/cop/style/comparable_between.rb +78 -0
- data/lib/rubocop/cop/style/comparable_clamp.rb +12 -1
- data/lib/rubocop/cop/style/concat_array_literals.rb +53 -9
- data/lib/rubocop/cop/style/conditional_assignment.rb +58 -24
- data/lib/rubocop/cop/style/constant_visibility.rb +23 -12
- data/lib/rubocop/cop/style/copyright.rb +27 -12
- data/lib/rubocop/cop/style/data_inheritance.rb +25 -0
- data/lib/rubocop/cop/style/date_time.rb +4 -4
- data/lib/rubocop/cop/style/def_with_parentheses.rb +22 -5
- data/lib/rubocop/cop/style/dig_chain.rb +6 -1
- data/lib/rubocop/cop/style/dir_empty.rb +4 -0
- data/lib/rubocop/cop/style/directive_scope.rb +304 -0
- data/lib/rubocop/cop/style/disable_cops_within_source_code_directive.rb +184 -20
- data/lib/rubocop/cop/style/document_dynamic_eval_definition.rb +6 -1
- data/lib/rubocop/cop/style/documentation.rb +53 -6
- data/lib/rubocop/cop/style/documentation_method.rb +8 -12
- data/lib/rubocop/cop/style/double_negation.rb +14 -3
- data/lib/rubocop/cop/style/each_for_simple_loop.rb +1 -1
- data/lib/rubocop/cop/style/each_with_object.rb +4 -3
- data/lib/rubocop/cop/style/empty_block_parameter.rb +1 -1
- data/lib/rubocop/cop/style/empty_case_condition.rb +13 -4
- data/lib/rubocop/cop/style/empty_class_definition.rb +126 -0
- data/lib/rubocop/cop/style/empty_heredoc.rb +4 -0
- data/lib/rubocop/cop/style/empty_lambda_parameter.rb +1 -1
- data/lib/rubocop/cop/style/empty_literal.rb +12 -3
- data/lib/rubocop/cop/style/empty_method.rb +15 -9
- data/lib/rubocop/cop/style/empty_string_inside_interpolation.rb +110 -0
- data/lib/rubocop/cop/style/encoding.rb +7 -1
- data/lib/rubocop/cop/style/end_block.rb +3 -1
- data/lib/rubocop/cop/style/endless_method.rb +252 -19
- data/lib/rubocop/cop/style/env_home.rb +4 -0
- data/lib/rubocop/cop/style/eval_with_location.rb +3 -3
- data/lib/rubocop/cop/style/even_odd.rb +11 -1
- data/lib/rubocop/cop/style/exact_regexp_match.rb +52 -8
- data/lib/rubocop/cop/style/expand_path_arguments.rb +2 -7
- data/lib/rubocop/cop/style/explicit_block_argument.rb +62 -9
- data/lib/rubocop/cop/style/exponential_notation.rb +5 -4
- data/lib/rubocop/cop/style/fetch_env_var.rb +33 -7
- data/lib/rubocop/cop/style/file_null.rb +6 -4
- data/lib/rubocop/cop/style/file_open.rb +84 -0
- data/lib/rubocop/cop/style/file_write.rb +21 -16
- data/lib/rubocop/cop/style/float_division.rb +43 -15
- data/lib/rubocop/cop/style/for.rb +48 -1
- data/lib/rubocop/cop/style/format_string.rb +44 -9
- data/lib/rubocop/cop/style/format_string_token.rb +86 -16
- data/lib/rubocop/cop/style/frozen_string_literal_comment.rb +5 -3
- data/lib/rubocop/cop/style/global_std_stream.rb +3 -0
- data/lib/rubocop/cop/style/global_vars.rb +5 -2
- data/lib/rubocop/cop/style/guard_clause.rb +41 -24
- data/lib/rubocop/cop/style/hash_as_last_array_item.rb +27 -9
- data/lib/rubocop/cop/style/hash_conversion.rb +52 -16
- data/lib/rubocop/cop/style/hash_each_methods.rb +4 -4
- data/lib/rubocop/cop/style/hash_fetch_chain.rb +104 -0
- data/lib/rubocop/cop/style/hash_lookup_method.rb +128 -0
- data/lib/rubocop/cop/style/hash_slice.rb +16 -0
- data/lib/rubocop/cop/style/hash_syntax.rb +23 -6
- data/lib/rubocop/cop/style/hash_transform_keys.rb +19 -9
- data/lib/rubocop/cop/style/hash_transform_values.rb +19 -9
- data/lib/rubocop/cop/style/identical_conditional_branches.rb +39 -11
- data/lib/rubocop/cop/style/if_inside_else.rb +46 -21
- data/lib/rubocop/cop/style/if_unless_modifier.rb +90 -66
- data/lib/rubocop/cop/style/if_unless_modifier_of_if_unless.rb +19 -19
- data/lib/rubocop/cop/style/if_with_boolean_literal_branches.rb +5 -2
- data/lib/rubocop/cop/style/if_with_semicolon.rb +61 -8
- data/lib/rubocop/cop/style/infinite_loop.rb +1 -1
- data/lib/rubocop/cop/style/inline_comment.rb +5 -2
- data/lib/rubocop/cop/style/inverse_methods.rb +34 -8
- data/lib/rubocop/cop/style/invertible_unless_condition.rb +27 -7
- data/lib/rubocop/cop/style/ip_addresses.rb +3 -4
- data/lib/rubocop/cop/style/it_assignment.rb +69 -12
- data/lib/rubocop/cop/style/it_block_parameter.rb +150 -0
- data/lib/rubocop/cop/style/keyword_arguments_merging.rb +4 -0
- data/lib/rubocop/cop/style/keyword_parameters_order.rb +23 -11
- data/lib/rubocop/cop/style/lambda.rb +30 -1
- data/lib/rubocop/cop/style/lambda_call.rb +31 -10
- data/lib/rubocop/cop/style/line_end_concatenation.rb +10 -4
- data/lib/rubocop/cop/style/magic_comment_format.rb +4 -4
- data/lib/rubocop/cop/style/map_compact_with_conditional_block.rb +11 -0
- data/lib/rubocop/cop/style/map_into_array.rb +6 -4
- data/lib/rubocop/cop/style/map_join.rb +123 -0
- data/lib/rubocop/cop/style/map_to_hash.rb +13 -5
- data/lib/rubocop/cop/style/map_to_set.rb +1 -3
- data/lib/rubocop/cop/style/method_call_with_args_parentheses/omit_parentheses.rb +75 -24
- data/lib/rubocop/cop/style/method_call_with_args_parentheses/require_parentheses.rb +15 -2
- data/lib/rubocop/cop/style/method_call_with_args_parentheses.rb +58 -6
- data/lib/rubocop/cop/style/method_call_without_args_parentheses.rb +36 -8
- data/lib/rubocop/cop/style/method_called_on_do_end_block.rb +2 -1
- data/lib/rubocop/cop/style/method_def_parentheses.rb +36 -8
- data/lib/rubocop/cop/style/min_max_comparison.rb +17 -6
- data/lib/rubocop/cop/style/missing_else.rb +7 -1
- data/lib/rubocop/cop/style/missing_respond_to_missing.rb +40 -7
- data/lib/rubocop/cop/style/mixin_usage.rb +1 -1
- data/lib/rubocop/cop/style/module_function.rb +4 -2
- data/lib/rubocop/cop/style/module_member_existence_check.rb +110 -0
- data/lib/rubocop/cop/style/multiline_block_chain.rb +2 -1
- data/lib/rubocop/cop/style/multiline_if_modifier.rb +47 -5
- data/lib/rubocop/cop/style/multiline_if_then.rb +10 -4
- data/lib/rubocop/cop/style/multiline_in_pattern_then.rb +7 -0
- data/lib/rubocop/cop/style/multiline_memoization.rb +7 -1
- data/lib/rubocop/cop/style/multiline_method_signature.rb +15 -22
- data/lib/rubocop/cop/style/multiline_ternary_operator.rb +7 -3
- data/lib/rubocop/cop/style/multiline_when_then.rb +7 -0
- data/lib/rubocop/cop/style/multiple_comparison.rb +33 -22
- data/lib/rubocop/cop/style/mutable_constant.rb +139 -13
- data/lib/rubocop/cop/style/negated_if_else_condition.rb +3 -3
- data/lib/rubocop/cop/style/negative_array_index.rb +228 -0
- data/lib/rubocop/cop/style/nested_modifier.rb +36 -12
- data/lib/rubocop/cop/style/nested_ternary_operator.rb +26 -8
- data/lib/rubocop/cop/style/next.rb +68 -10
- data/lib/rubocop/cop/style/nil_comparison.rb +53 -13
- data/lib/rubocop/cop/style/nil_lambda.rb +9 -1
- data/lib/rubocop/cop/style/non_nil_check.rb +21 -11
- data/lib/rubocop/cop/style/not.rb +12 -3
- data/lib/rubocop/cop/style/numeric_literal_prefix.rb +11 -1
- data/lib/rubocop/cop/style/numeric_literals.rb +3 -2
- data/lib/rubocop/cop/style/numeric_predicate.rb +22 -6
- data/lib/rubocop/cop/style/object_then.rb +1 -0
- data/lib/rubocop/cop/style/one_class_per_file.rb +115 -0
- data/lib/rubocop/cop/style/one_line_conditional.rb +35 -15
- data/lib/rubocop/cop/style/open_struct_use.rb +1 -1
- data/lib/rubocop/cop/style/operator_method_call.rb +10 -2
- data/lib/rubocop/cop/style/option_hash.rb +1 -1
- data/lib/rubocop/cop/style/optional_arguments.rb +1 -0
- data/lib/rubocop/cop/style/parallel_assignment.rb +58 -27
- data/lib/rubocop/cop/style/parentheses_around_condition.rb +6 -1
- data/lib/rubocop/cop/style/partition_instead_of_double_select.rb +270 -0
- data/lib/rubocop/cop/style/percent_literal_delimiters.rb +18 -3
- data/lib/rubocop/cop/style/percent_q_literals.rb +1 -1
- data/lib/rubocop/cop/style/perl_backrefs.rb +5 -3
- data/lib/rubocop/cop/style/predicate_with_kind.rb +84 -0
- data/lib/rubocop/cop/style/preferred_hash_methods.rb +12 -12
- data/lib/rubocop/cop/style/proc.rb +4 -2
- data/lib/rubocop/cop/style/raise_args.rb +9 -9
- data/lib/rubocop/cop/style/reduce_to_hash.rb +216 -0
- data/lib/rubocop/cop/style/redundant_argument.rb +2 -0
- data/lib/rubocop/cop/style/redundant_array_constructor.rb +2 -2
- data/lib/rubocop/cop/style/redundant_array_flatten.rb +50 -0
- data/lib/rubocop/cop/style/redundant_assignment.rb +12 -2
- data/lib/rubocop/cop/style/redundant_begin.rb +58 -6
- data/lib/rubocop/cop/style/redundant_condition.rb +93 -18
- data/lib/rubocop/cop/style/redundant_constant_base.rb +42 -6
- data/lib/rubocop/cop/style/redundant_current_directory_in_path.rb +26 -4
- data/lib/rubocop/cop/style/redundant_double_splat_hash_braces.rb +17 -3
- data/lib/rubocop/cop/style/redundant_each.rb +4 -5
- data/lib/rubocop/cop/style/redundant_exception.rb +22 -4
- data/lib/rubocop/cop/style/redundant_fetch_block.rb +11 -11
- data/lib/rubocop/cop/style/redundant_file_extension_in_require.rb +9 -0
- data/lib/rubocop/cop/style/redundant_filter_chain.rb +1 -1
- data/lib/rubocop/cop/style/redundant_format.rb +319 -0
- data/lib/rubocop/cop/style/redundant_freeze.rb +12 -3
- data/lib/rubocop/cop/style/redundant_heredoc_delimiter_quotes.rb +6 -1
- data/lib/rubocop/cop/style/redundant_interpolation.rb +12 -3
- data/lib/rubocop/cop/style/redundant_interpolation_unfreeze.rb +26 -10
- data/lib/rubocop/cop/style/redundant_line_continuation.rb +83 -119
- data/lib/rubocop/cop/style/redundant_min_max_by.rb +93 -0
- data/lib/rubocop/cop/style/redundant_parentheses.rb +176 -83
- data/lib/rubocop/cop/style/redundant_percent_q.rb +5 -3
- data/lib/rubocop/cop/style/redundant_regexp_argument.rb +15 -0
- data/lib/rubocop/cop/style/redundant_regexp_character_class.rb +6 -5
- data/lib/rubocop/cop/style/redundant_regexp_constructor.rb +27 -7
- data/lib/rubocop/cop/style/redundant_regexp_escape.rb +16 -0
- data/lib/rubocop/cop/style/redundant_return.rb +4 -3
- data/lib/rubocop/cop/style/redundant_self.rb +20 -7
- data/lib/rubocop/cop/style/redundant_self_assignment.rb +2 -3
- data/lib/rubocop/cop/style/redundant_self_assignment_branch.rb +0 -5
- data/lib/rubocop/cop/style/redundant_sort.rb +7 -7
- data/lib/rubocop/cop/style/redundant_sort_by.rb +17 -1
- data/lib/rubocop/cop/style/redundant_string_escape.rb +1 -2
- data/lib/rubocop/cop/style/redundant_struct_keyword_init.rb +133 -0
- data/lib/rubocop/cop/style/regexp_literal.rb +107 -29
- data/lib/rubocop/cop/style/require_order.rb +9 -0
- data/lib/rubocop/cop/style/rescue_modifier.rb +10 -12
- data/lib/rubocop/cop/style/return_nil.rb +19 -4
- data/lib/rubocop/cop/style/return_nil_in_predicate_method_definition.rb +11 -1
- data/lib/rubocop/cop/style/reverse_find.rb +51 -0
- data/lib/rubocop/cop/style/safe_navigation.rb +76 -20
- data/lib/rubocop/cop/style/sample.rb +19 -13
- data/lib/rubocop/cop/style/select_by_kind.rb +158 -0
- data/lib/rubocop/cop/style/select_by_range.rb +197 -0
- data/lib/rubocop/cop/style/select_by_regexp.rb +54 -22
- data/lib/rubocop/cop/style/self_assignment.rb +13 -16
- data/lib/rubocop/cop/style/semicolon.rb +56 -14
- data/lib/rubocop/cop/style/single_line_block_params.rb +2 -2
- data/lib/rubocop/cop/style/single_line_do_end_block.rb +22 -8
- data/lib/rubocop/cop/style/single_line_methods.rb +28 -11
- data/lib/rubocop/cop/style/sole_nested_conditional.rb +96 -104
- data/lib/rubocop/cop/style/special_global_vars.rb +7 -2
- data/lib/rubocop/cop/style/stabby_lambda_parentheses.rb +32 -6
- data/lib/rubocop/cop/style/static_class.rb +21 -0
- data/lib/rubocop/cop/style/string_concatenation.rb +38 -16
- data/lib/rubocop/cop/style/string_hash_keys.rb +1 -0
- data/lib/rubocop/cop/style/struct_inheritance.rb +38 -2
- data/lib/rubocop/cop/style/super_arguments.rb +7 -6
- data/lib/rubocop/cop/style/symbol_array.rb +1 -1
- data/lib/rubocop/cop/style/symbol_proc.rb +34 -14
- data/lib/rubocop/cop/style/tally_method.rb +181 -0
- data/lib/rubocop/cop/style/ternary_parentheses.rb +34 -1
- data/lib/rubocop/cop/style/time_now.rb +41 -0
- data/lib/rubocop/cop/style/top_level_method_definition.rb +3 -2
- data/lib/rubocop/cop/style/trailing_comma_in_arguments.rb +52 -1
- data/lib/rubocop/cop/style/trailing_comma_in_array_literal.rb +47 -6
- data/lib/rubocop/cop/style/trailing_comma_in_block_args.rb +2 -2
- data/lib/rubocop/cop/style/trailing_comma_in_hash_literal.rb +48 -6
- data/lib/rubocop/cop/style/trailing_method_end_statement.rb +1 -0
- data/lib/rubocop/cop/style/trailing_underscore_variable.rb +35 -32
- data/lib/rubocop/cop/style/trivial_accessors.rb +2 -2
- data/lib/rubocop/cop/style/unless_else.rb +10 -9
- data/lib/rubocop/cop/style/unless_logical_operators.rb +3 -3
- data/lib/rubocop/cop/style/while_until_do.rb +7 -0
- data/lib/rubocop/cop/style/while_until_modifier.rb +16 -1
- data/lib/rubocop/cop/style/word_array.rb +1 -0
- data/lib/rubocop/cop/style/yoda_condition.rb +26 -12
- data/lib/rubocop/cop/style/yoda_expression.rb +11 -2
- data/lib/rubocop/cop/style/zero_length_predicate.rb +6 -3
- data/lib/rubocop/cop/style.rb +311 -0
- data/lib/rubocop/cop/team.rb +172 -49
- data/lib/rubocop/cop/util.rb +7 -10
- data/lib/rubocop/cop/utils/format_string.rb +20 -5
- data/lib/rubocop/cop/variable_force/assignment.rb +8 -4
- data/lib/rubocop/cop/variable_force/branch.rb +30 -6
- data/lib/rubocop/cop/variable_force/scope.rb +1 -1
- data/lib/rubocop/cop/variable_force/variable.rb +42 -11
- data/lib/rubocop/cop/variable_force.rb +26 -9
- data/lib/rubocop/cops_documentation_generator.rb +49 -15
- data/lib/rubocop/directive_comment.rb +147 -5
- data/lib/rubocop/ext/regexp_node.rb +0 -1
- data/lib/rubocop/feature_loader.rb +0 -6
- data/lib/rubocop/file_patterns.rb +9 -1
- data/lib/rubocop/formatter/base_formatter.rb +22 -0
- data/lib/rubocop/formatter/clang_style_formatter.rb +5 -2
- data/lib/rubocop/formatter/disabled_config_formatter.rb +57 -14
- data/lib/rubocop/formatter/emacs_style_formatter.rb +3 -1
- data/lib/rubocop/formatter/formatter_set.rb +7 -2
- data/lib/rubocop/formatter/fuubar_style_formatter.rb +1 -1
- data/lib/rubocop/formatter/github_actions_formatter.rb +6 -5
- data/lib/rubocop/formatter/html_formatter.rb +3 -5
- data/lib/rubocop/formatter/json_formatter.rb +82 -7
- data/lib/rubocop/formatter/junit_formatter.rb +27 -10
- data/lib/rubocop/formatter/markdown_formatter.rb +1 -0
- data/lib/rubocop/formatter/offense_count_formatter.rb +5 -4
- data/lib/rubocop/formatter/pacman_formatter.rb +5 -2
- data/lib/rubocop/formatter/sarif_formatter.rb +186 -0
- data/lib/rubocop/formatter/simple_text_formatter.rb +4 -5
- data/lib/rubocop/formatter/tap_formatter.rb +8 -3
- data/lib/rubocop/formatter/worst_offenders_formatter.rb +5 -4
- data/lib/rubocop/formatter.rb +23 -21
- data/lib/rubocop/lockfile.rb +18 -0
- data/lib/rubocop/lsp/diagnostic.rb +22 -41
- data/lib/rubocop/lsp/disable_comment_edits.rb +135 -0
- data/lib/rubocop/lsp/routes.rb +136 -33
- data/lib/rubocop/lsp/runtime.rb +66 -15
- data/lib/rubocop/lsp/server.rb +4 -2
- data/lib/rubocop/lsp/stdin_runner.rb +38 -19
- data/lib/rubocop/lsp.rb +5 -2
- data/lib/rubocop/magic_comment.rb +55 -0
- data/lib/rubocop/mcp/autocorrection_request.rb +52 -0
- data/lib/rubocop/mcp/explain_tool.rb +68 -0
- data/lib/rubocop/mcp/scope.rb +65 -0
- data/lib/rubocop/mcp/server.rb +307 -0
- data/lib/rubocop/mcp/source_files.rb +35 -0
- data/lib/rubocop/offense_limit.rb +30 -0
- data/lib/rubocop/options.rb +166 -23
- data/lib/rubocop/path_util.rb +20 -5
- data/lib/rubocop/pending_cops_reporter.rb +51 -0
- data/lib/rubocop/plugin/configuration_integrator.rb +153 -0
- data/lib/rubocop/plugin/load_error.rb +26 -0
- data/lib/rubocop/plugin/loader.rb +100 -0
- data/lib/rubocop/plugin/not_supported_error.rb +29 -0
- data/lib/rubocop/plugin.rb +46 -0
- data/lib/rubocop/project_index_loader.rb +82 -0
- data/lib/rubocop/rake_task.rb +6 -4
- data/lib/rubocop/remote_config.rb +18 -13
- data/lib/rubocop/result_cache.rb +110 -65
- data/lib/rubocop/rspec/cop_helper.rb +21 -1
- data/lib/rubocop/rspec/expect_offense.rb +11 -7
- data/lib/rubocop/rspec/shared_contexts.rb +85 -3
- data/lib/rubocop/rspec/support.rb +4 -0
- data/lib/rubocop/runner.rb +368 -106
- data/lib/rubocop/server/cache.rb +67 -48
- data/lib/rubocop/server/cli.rb +2 -4
- data/lib/rubocop/server/client_command/base.rb +10 -0
- data/lib/rubocop/server/client_command/exec.rb +2 -1
- data/lib/rubocop/server/client_command/start.rb +11 -1
- data/lib/rubocop/server/core.rb +8 -0
- data/lib/rubocop/server.rb +14 -0
- data/lib/rubocop/target_finder.rb +25 -11
- data/lib/rubocop/target_ruby.rb +31 -14
- data/lib/rubocop/todo_audit.rb +111 -0
- data/lib/rubocop/unified_diff.rb +257 -0
- data/lib/rubocop/util.rb +69 -0
- data/lib/rubocop/version.rb +48 -10
- data/lib/rubocop.rb +35 -682
- data/lib/ruby_lsp/rubocop/addon.rb +28 -17
- data/lib/ruby_lsp/rubocop/runtime_adapter.rb +99 -0
- metadata +129 -21
- data/lib/rubocop/cop/style/double_cop_disable_directive.rb +0 -46
- data/lib/rubocop/cop/utils/regexp_ranges.rb +0 -113
- data/lib/ruby_lsp/rubocop/wraps_built_in_lsp_runtime.rb +0 -50
|
@@ -13,17 +13,17 @@ module RuboCop
|
|
|
13
13
|
# # good
|
|
14
14
|
# x if y.z.nil?
|
|
15
15
|
#
|
|
16
|
-
class RedundantParentheses < Base
|
|
16
|
+
class RedundantParentheses < Base # rubocop:disable Metrics/ClassLength
|
|
17
17
|
include Parentheses
|
|
18
|
+
include ReparsedEquivalence
|
|
18
19
|
extend AutoCorrector
|
|
19
20
|
|
|
20
|
-
ALLOWED_NODE_TYPES = %i[
|
|
21
|
+
ALLOWED_NODE_TYPES = %i[or send splat kwsplat].freeze
|
|
21
22
|
|
|
22
23
|
# @!method square_brackets?(node)
|
|
23
|
-
def_node_matcher :square_brackets?,
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
def_node_matcher :method_node_and_args, '$(call _recv _msg $...)'
|
|
24
|
+
def_node_matcher :square_brackets?, <<~PATTERN
|
|
25
|
+
(send `{(send _recv _msg) str array hash const #variable?} :[] ...)
|
|
26
|
+
PATTERN
|
|
27
27
|
|
|
28
28
|
# @!method rescue?(node)
|
|
29
29
|
def_node_matcher :rescue?, '{^resbody ^^resbody}'
|
|
@@ -31,20 +31,43 @@ module RuboCop
|
|
|
31
31
|
# @!method allowed_pin_operator?(node)
|
|
32
32
|
def_node_matcher :allowed_pin_operator?, '^(pin (begin !{lvar ivar cvar gvar}))'
|
|
33
33
|
|
|
34
|
+
def on_new_investigation
|
|
35
|
+
@pending_offenses = {}.compare_by_identity
|
|
36
|
+
super
|
|
37
|
+
end
|
|
38
|
+
|
|
34
39
|
def on_begin(node)
|
|
35
40
|
return if !parentheses?(node) || parens_allowed?(node) || ignore_syntax?(node)
|
|
36
41
|
|
|
37
42
|
check(node)
|
|
38
43
|
end
|
|
39
44
|
|
|
45
|
+
def on_investigation_end
|
|
46
|
+
# Each candidate's exact correction is verified by reparsing before
|
|
47
|
+
# the offense is registered, so redundancy never depends on
|
|
48
|
+
# hand-maintained knowledge of Ruby's grammar.
|
|
49
|
+
verified_by_reparse(@pending_offenses.keys).each do |node|
|
|
50
|
+
add_offense(node, message: @pending_offenses[node]) do |corrector|
|
|
51
|
+
ParenthesesCorrector.correct(corrector, node)
|
|
52
|
+
end
|
|
53
|
+
end
|
|
54
|
+
|
|
55
|
+
super
|
|
56
|
+
end
|
|
57
|
+
|
|
40
58
|
private
|
|
41
59
|
|
|
60
|
+
def variable?(node)
|
|
61
|
+
node.respond_to?(:variable?) && node.variable?
|
|
62
|
+
end
|
|
63
|
+
|
|
42
64
|
def parens_allowed?(node)
|
|
43
65
|
empty_parentheses?(node) ||
|
|
44
|
-
first_arg_begins_with_hash_literal?(node) ||
|
|
45
66
|
rescue?(node) ||
|
|
67
|
+
in_pattern_matching_in_method_argument?(node) ||
|
|
46
68
|
allowed_pin_operator?(node) ||
|
|
47
|
-
allowed_expression?(node)
|
|
69
|
+
allowed_expression?(node) ||
|
|
70
|
+
ParenthesesCorrector.heredoc_strands_code_after_close_paren?(node)
|
|
48
71
|
end
|
|
49
72
|
|
|
50
73
|
def ignore_syntax?(node)
|
|
@@ -72,7 +95,7 @@ module RuboCop
|
|
|
72
95
|
ancestor = node.ancestors.first
|
|
73
96
|
return false unless ancestor
|
|
74
97
|
|
|
75
|
-
!ancestor.type?(:begin, :
|
|
98
|
+
!ancestor.type?(:begin, :any_def, :any_block)
|
|
76
99
|
end
|
|
77
100
|
|
|
78
101
|
def allowed_ternary?(node)
|
|
@@ -92,7 +115,7 @@ module RuboCop
|
|
|
92
115
|
return false unless node.type?(:send, :super, :yield)
|
|
93
116
|
|
|
94
117
|
node.arguments.one? && !node.parenthesized? &&
|
|
95
|
-
!node.
|
|
118
|
+
!node.operator_method? && node.first_argument.begin_type?
|
|
96
119
|
end
|
|
97
120
|
|
|
98
121
|
def multiline_control_flow_statements?(node)
|
|
@@ -107,46 +130,52 @@ module RuboCop
|
|
|
107
130
|
node.children.empty?
|
|
108
131
|
end
|
|
109
132
|
|
|
110
|
-
def
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
if (root_method = node.each_ancestor(:send).to_a.last)
|
|
114
|
-
parenthesized = root_method.parenthesized_call?
|
|
115
|
-
end
|
|
116
|
-
hash_literal && first_argument?(node) && !parentheses?(hash_literal) && !parenthesized
|
|
117
|
-
end
|
|
133
|
+
def in_pattern_matching_in_method_argument?(begin_node)
|
|
134
|
+
return false unless begin_node.parent&.call_type?
|
|
135
|
+
return false unless (node = begin_node.children.first)
|
|
118
136
|
|
|
119
|
-
|
|
120
|
-
return if node.nil?
|
|
121
|
-
return node if node.hash_type?
|
|
122
|
-
return unless node.send_type?
|
|
123
|
-
|
|
124
|
-
method_chain_begins_with_hash_literal(node.children.first)
|
|
137
|
+
target_ruby_version <= 2.7 ? node.match_pattern_type? : node.match_pattern_p_type?
|
|
125
138
|
end
|
|
126
139
|
|
|
127
140
|
def check(begin_node)
|
|
128
141
|
node = begin_node.children.first
|
|
129
142
|
|
|
130
143
|
if (message = find_offense_message(begin_node, node))
|
|
144
|
+
return offense(begin_node, message) if message == 'block body'
|
|
145
|
+
|
|
146
|
+
if node.range_type? && !argument_of_parenthesized_method_call?(begin_node, node)
|
|
147
|
+
begin_node = begin_node.parent
|
|
148
|
+
end
|
|
149
|
+
|
|
131
150
|
return offense(begin_node, message)
|
|
132
151
|
end
|
|
133
152
|
|
|
134
|
-
check_send(begin_node, node) if node
|
|
153
|
+
check_send(begin_node, node) if call_node?(node)
|
|
135
154
|
end
|
|
136
155
|
|
|
137
|
-
# rubocop:disable Metrics/AbcSize, Metrics/CyclomaticComplexity, Metrics/MethodLength, Metrics/PerceivedComplexity
|
|
156
|
+
# rubocop:disable-next Metrics/AbcSize, Metrics/CyclomaticComplexity, Metrics/MethodLength, Metrics/PerceivedComplexity
|
|
138
157
|
def find_offense_message(begin_node, node)
|
|
139
158
|
return 'a keyword' if keyword_with_redundant_parentheses?(node)
|
|
140
|
-
return 'a literal' if disallowed_literal?(begin_node, node)
|
|
159
|
+
return 'a literal' if node.literal? && disallowed_literal?(begin_node, node)
|
|
141
160
|
return 'a variable' if node.variable?
|
|
142
161
|
return 'a constant' if node.const_type?
|
|
162
|
+
return 'block body' if begin_node.parent&.any_block_type? || body_range?(begin_node, node)
|
|
163
|
+
|
|
143
164
|
if node.assignment? && (begin_node.parent.nil? || begin_node.parent.begin_type?)
|
|
144
165
|
return 'an assignment'
|
|
145
166
|
end
|
|
146
167
|
if node.lambda_or_proc? && (node.braces? || node.send_node.lambda_literal?)
|
|
147
168
|
return 'an expression'
|
|
148
169
|
end
|
|
170
|
+
if disallowed_one_line_pattern_matching?(begin_node, node)
|
|
171
|
+
return 'a one-line pattern matching'
|
|
172
|
+
end
|
|
149
173
|
return 'an interpolated expression' if interpolation?(begin_node)
|
|
174
|
+
if argument_of_parenthesized_method_call?(begin_node, node) &&
|
|
175
|
+
!keyword_logical_operator?(node)
|
|
176
|
+
return 'a method argument'
|
|
177
|
+
end
|
|
178
|
+
return 'a one-line rescue' if oneline_rescue_parentheses_required?(begin_node, node)
|
|
150
179
|
|
|
151
180
|
return if begin_node.chained?
|
|
152
181
|
|
|
@@ -154,6 +183,7 @@ module RuboCop
|
|
|
154
183
|
return if node.semantic_operator? && begin_node.parent
|
|
155
184
|
return if node.multiline? && allow_in_multiline_conditions?
|
|
156
185
|
return if ALLOWED_NODE_TYPES.include?(begin_node.parent&.type)
|
|
186
|
+
return if !node.and_type? && begin_node.parent&.and_type?
|
|
157
187
|
return if begin_node.parent&.if_type? && begin_node.parent.ternary?
|
|
158
188
|
|
|
159
189
|
'a logical expression'
|
|
@@ -163,41 +193,116 @@ module RuboCop
|
|
|
163
193
|
'a comparison expression'
|
|
164
194
|
end
|
|
165
195
|
end
|
|
166
|
-
# rubocop:enable Metrics/AbcSize, Metrics/CyclomaticComplexity, Metrics/MethodLength, Metrics/PerceivedComplexity
|
|
167
196
|
|
|
168
197
|
# @!method interpolation?(node)
|
|
169
198
|
def_node_matcher :interpolation?, '[^begin ^^dstr]'
|
|
170
199
|
|
|
200
|
+
def argument_of_parenthesized_method_call?(begin_node, node)
|
|
201
|
+
if node.basic_conditional? || node.rescue_type? || method_call_parentheses_required?(node)
|
|
202
|
+
return false
|
|
203
|
+
end
|
|
204
|
+
return false unless (parent = begin_node.parent)
|
|
205
|
+
|
|
206
|
+
parent.call_type? && parent.parenthesized? && parent.receiver != begin_node
|
|
207
|
+
end
|
|
208
|
+
|
|
209
|
+
def oneline_rescue_parentheses_required?(begin_node, node)
|
|
210
|
+
return false unless node.rescue_type?
|
|
211
|
+
return false unless (parent = begin_node.parent)
|
|
212
|
+
return false if parent.if_type? && parent.ternary?
|
|
213
|
+
return false if parent.conditional? && parent.condition == begin_node
|
|
214
|
+
|
|
215
|
+
!parent.type?(:call, :array, :pair)
|
|
216
|
+
end
|
|
217
|
+
|
|
218
|
+
def method_call_parentheses_required?(node)
|
|
219
|
+
return false unless node.call_type?
|
|
220
|
+
|
|
221
|
+
(node.receiver.nil? || node.loc.dot) && node.arguments.any?
|
|
222
|
+
end
|
|
223
|
+
|
|
171
224
|
def allow_in_multiline_conditions?
|
|
172
225
|
!!config.for_enabled_cop('Style/ParenthesesAroundCondition')['AllowInMultilineConditions']
|
|
173
226
|
end
|
|
174
227
|
|
|
228
|
+
def call_node?(node)
|
|
229
|
+
node.call_type? || (node.any_block_type? && node.braces? && !node.lambda_or_proc?)
|
|
230
|
+
end
|
|
231
|
+
|
|
175
232
|
def check_send(begin_node, node)
|
|
233
|
+
node = node.send_node if node.any_block_type?
|
|
234
|
+
|
|
176
235
|
return check_unary(begin_node, node) if node.unary_operation?
|
|
236
|
+
return if setter_in_condition?(begin_node, node)
|
|
177
237
|
|
|
178
|
-
return unless method_call_with_redundant_parentheses?(node)
|
|
179
|
-
return if call_chain_starts_with_int?(begin_node, node) ||
|
|
180
|
-
do_end_block_in_method_chain?(begin_node, node)
|
|
238
|
+
return unless method_call_with_redundant_parentheses?(begin_node, node)
|
|
181
239
|
|
|
182
240
|
offense(begin_node, 'a method call')
|
|
183
241
|
end
|
|
184
242
|
|
|
243
|
+
# Like a variable assignment, `if (foo.bar = baz)` is a safe assignment
|
|
244
|
+
# that `Lint/AssignmentInCondition` asks for, not redundant parentheses.
|
|
245
|
+
def setter_in_condition?(begin_node, node)
|
|
246
|
+
return false unless node.setter_method?
|
|
247
|
+
return false unless (parent = begin_node.parent)&.basic_conditional?
|
|
248
|
+
|
|
249
|
+
parent.condition.equal?(begin_node)
|
|
250
|
+
end
|
|
251
|
+
|
|
185
252
|
def check_unary(begin_node, node)
|
|
186
253
|
return if begin_node.chained?
|
|
187
254
|
|
|
188
255
|
node = node.children.first while suspect_unary?(node)
|
|
189
|
-
|
|
190
|
-
return if node.send_type? && !method_call_with_redundant_parentheses?(node)
|
|
256
|
+
return unless method_call_with_redundant_parentheses?(begin_node, node)
|
|
191
257
|
|
|
192
258
|
offense(begin_node, 'a unary operation')
|
|
193
259
|
end
|
|
194
260
|
|
|
195
261
|
def offense(node, msg)
|
|
196
|
-
|
|
197
|
-
|
|
262
|
+
@pending_offenses[node] = "Don't use parentheses around #{msg}."
|
|
263
|
+
end
|
|
264
|
+
|
|
265
|
+
def apply_reparse_correction(corrector, node)
|
|
266
|
+
ParenthesesCorrector.correct(corrector, node)
|
|
267
|
+
end
|
|
268
|
+
|
|
269
|
+
# Grouping parentheses are transparent to the comparison: single-child
|
|
270
|
+
# `begin` nodes are collapsed, a parenthesized statement sequence
|
|
271
|
+
# inside another sequence is spliced in place, and chains of the same
|
|
272
|
+
# `&&`/`||` operator are normalized to left association (`x && (y &&
|
|
273
|
+
# z)` and `x && y && z` differ as trees but `&&` and `||` cannot be
|
|
274
|
+
# redefined, so same-operator regrouping is semantically transparent).
|
|
275
|
+
def normalize_reparsed_ast(node)
|
|
276
|
+
return node unless node.is_a?(::Parser::AST::Node)
|
|
277
|
+
|
|
278
|
+
children = node.children.map { |child| normalize_reparsed_ast(child) }
|
|
279
|
+
children = splice_nested_sequences(children) if %i[begin kwbegin].include?(node.type)
|
|
280
|
+
|
|
281
|
+
node = node.updated(nil, children)
|
|
282
|
+
if node.begin_type? && children.one? && children.first.is_a?(::Parser::AST::Node)
|
|
283
|
+
children.first
|
|
284
|
+
else
|
|
285
|
+
rotate_same_operator(node)
|
|
198
286
|
end
|
|
199
287
|
end
|
|
200
288
|
|
|
289
|
+
def splice_nested_sequences(children)
|
|
290
|
+
children.flat_map do |child|
|
|
291
|
+
child.is_a?(::Parser::AST::Node) && child.begin_type? ? child.children : [child]
|
|
292
|
+
end
|
|
293
|
+
end
|
|
294
|
+
|
|
295
|
+
def rotate_same_operator(node)
|
|
296
|
+
return node unless node.type?(:and, :or)
|
|
297
|
+
|
|
298
|
+
right = node.rhs
|
|
299
|
+
return node unless right.is_a?(::Parser::AST::Node) && right.type == node.type
|
|
300
|
+
|
|
301
|
+
rotated_left = rotate_same_operator(node.updated(nil, [node.lhs, right.lhs]))
|
|
302
|
+
|
|
303
|
+
rotate_same_operator(node.updated(nil, [rotated_left, right.rhs]))
|
|
304
|
+
end
|
|
305
|
+
|
|
201
306
|
def suspect_unary?(node)
|
|
202
307
|
node.send_type? && node.unary_operation? && !node.prefix_not?
|
|
203
308
|
end
|
|
@@ -207,18 +312,37 @@ module RuboCop
|
|
|
207
312
|
end
|
|
208
313
|
|
|
209
314
|
def disallowed_literal?(begin_node, node)
|
|
210
|
-
|
|
315
|
+
return true unless node.range_type?
|
|
316
|
+
return false unless (parent = begin_node.parent)
|
|
317
|
+
|
|
318
|
+
parent.begin_type? && parent.children.one?
|
|
211
319
|
end
|
|
212
320
|
|
|
213
|
-
|
|
214
|
-
|
|
321
|
+
# rubocop:disable-next Metrics/CyclomaticComplexity
|
|
322
|
+
def body_range?(begin_node, node)
|
|
323
|
+
return false if begin_node.chained?
|
|
324
|
+
return false unless node.range_type?
|
|
325
|
+
return false unless (parent = begin_node.parent)
|
|
326
|
+
return false unless parent.begin_type?
|
|
215
327
|
|
|
216
|
-
|
|
217
|
-
|
|
328
|
+
(node.begin.nil? && begin_node == parent.children.first) ||
|
|
329
|
+
(node.end.nil? && begin_node == parent.children.last)
|
|
330
|
+
end
|
|
331
|
+
|
|
332
|
+
# `and`/`or` keyword operators bind looser than the method-argument
|
|
333
|
+
# boundary, so `foo((x and y))` cannot drop its parentheses without
|
|
334
|
+
# becoming a syntax error (unlike `&&`/`||`).
|
|
335
|
+
def keyword_logical_operator?(node)
|
|
336
|
+
node.operator_keyword? && node.semantic_operator?
|
|
337
|
+
end
|
|
218
338
|
|
|
219
|
-
|
|
339
|
+
def disallowed_one_line_pattern_matching?(begin_node, node)
|
|
340
|
+
if (parent = begin_node.parent)
|
|
341
|
+
return false if parent.any_def_type? && parent.endless?
|
|
342
|
+
return false if parent.assignment?
|
|
343
|
+
end
|
|
220
344
|
|
|
221
|
-
|
|
345
|
+
node.any_match_pattern_type? && node.each_ancestor.none?(&:operator_keyword?)
|
|
222
346
|
end
|
|
223
347
|
|
|
224
348
|
def keyword_with_redundant_parentheses?(node)
|
|
@@ -234,54 +358,23 @@ module RuboCop
|
|
|
234
358
|
end
|
|
235
359
|
end
|
|
236
360
|
|
|
237
|
-
def method_call_with_redundant_parentheses?(node)
|
|
238
|
-
return false unless node.
|
|
361
|
+
def method_call_with_redundant_parentheses?(begin_node, node)
|
|
362
|
+
return false unless node.type?(:call, :super, :yield, :defined?)
|
|
239
363
|
return false if node.prefix_not?
|
|
364
|
+
return true if singular_parenthesized_parent?(begin_node)
|
|
240
365
|
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
args.empty? || parentheses?(send_node) || square_brackets?(send_node)
|
|
244
|
-
end
|
|
245
|
-
|
|
246
|
-
def only_begin_arg?(args)
|
|
247
|
-
args.one? && args.first&.begin_type?
|
|
248
|
-
end
|
|
249
|
-
|
|
250
|
-
def first_argument?(node)
|
|
251
|
-
if first_send_argument?(node) ||
|
|
252
|
-
first_super_argument?(node) ||
|
|
253
|
-
first_yield_argument?(node)
|
|
254
|
-
return true
|
|
255
|
-
end
|
|
256
|
-
|
|
257
|
-
node.each_ancestor.any? { |ancestor| first_argument?(ancestor) }
|
|
366
|
+
node.arguments.empty? || parentheses?(node) || square_brackets?(node)
|
|
258
367
|
end
|
|
259
368
|
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
PATTERN
|
|
369
|
+
def singular_parenthesized_parent?(begin_node)
|
|
370
|
+
return true unless (parent = begin_node.parent)
|
|
371
|
+
return false if parent.type?(:splat, :kwsplat)
|
|
264
372
|
|
|
265
|
-
|
|
266
|
-
def_node_matcher :first_super_argument?, <<~PATTERN
|
|
267
|
-
^(super equal?(%0) ...)
|
|
268
|
-
PATTERN
|
|
269
|
-
|
|
270
|
-
# @!method first_yield_argument?(node)
|
|
271
|
-
def_node_matcher :first_yield_argument?, <<~PATTERN
|
|
272
|
-
^(yield equal?(%0) ...)
|
|
273
|
-
PATTERN
|
|
274
|
-
|
|
275
|
-
def call_chain_starts_with_int?(begin_node, send_node)
|
|
276
|
-
recv = first_part_of_call_chain(send_node)
|
|
277
|
-
recv&.int_type? && (parent = begin_node.parent) &&
|
|
278
|
-
parent.send_type? && (parent.method?(:-@) || parent.method?(:+@))
|
|
373
|
+
parent.children.one?
|
|
279
374
|
end
|
|
280
375
|
|
|
281
|
-
def
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
block.keywords? && begin_node.each_ancestor(:call).any?
|
|
376
|
+
def only_begin_arg?(args)
|
|
377
|
+
args.one? && args.first&.begin_type?
|
|
285
378
|
end
|
|
286
379
|
end
|
|
287
380
|
end
|
|
@@ -80,8 +80,7 @@ module RuboCop
|
|
|
80
80
|
end
|
|
81
81
|
|
|
82
82
|
def string_literal?(node)
|
|
83
|
-
node.loc
|
|
84
|
-
node.loc.begin && node.loc.end
|
|
83
|
+
node.loc?(:begin) && node.loc?(:end)
|
|
85
84
|
end
|
|
86
85
|
|
|
87
86
|
def start_with_percent_q_variant?(string)
|
|
@@ -91,7 +90,10 @@ module RuboCop
|
|
|
91
90
|
def acceptable_q?(node)
|
|
92
91
|
src = node.source
|
|
93
92
|
|
|
94
|
-
|
|
93
|
+
# If the string contains interpolation-like syntax and would be
|
|
94
|
+
# converted to a double-quoted string (because it contains single
|
|
95
|
+
# quotes), the replacement would activate interpolation.
|
|
96
|
+
return true if STRING_INTERPOLATION_REGEXP.match?(src) && src.include?(SINGLE_QUOTE)
|
|
95
97
|
|
|
96
98
|
src.scan(/\\./).any?(ESCAPED_NON_BACKSLASH)
|
|
97
99
|
end
|
|
@@ -66,6 +66,7 @@ module RuboCop
|
|
|
66
66
|
DETERMINISTIC_REGEX.match?(regexp_node.source)
|
|
67
67
|
end
|
|
68
68
|
|
|
69
|
+
# rubocop:disable-next Metrics/MethodLength
|
|
69
70
|
def preferred_argument(regexp_node)
|
|
70
71
|
new_argument = replacement(regexp_node)
|
|
71
72
|
|
|
@@ -73,6 +74,13 @@ module RuboCop
|
|
|
73
74
|
new_argument.gsub!("'", "\\\\'")
|
|
74
75
|
new_argument.gsub!('\"', '"')
|
|
75
76
|
quote = "'"
|
|
77
|
+
elsif new_argument.include?("\\'")
|
|
78
|
+
# Add a backslash before single quotes preceded by an even number of backslashes.
|
|
79
|
+
# An even number (including zero) of backslashes before a quote means the quote itself
|
|
80
|
+
# is not escaped.
|
|
81
|
+
# Otherwise an odd number means the quote is already escaped so this doesn't touch it.
|
|
82
|
+
new_argument.gsub!(/(?<!\\)((?:\\\\)*)'/) { "#{::Regexp.last_match(1)}\\'" }
|
|
83
|
+
quote = "'"
|
|
76
84
|
elsif new_argument.include?('\'')
|
|
77
85
|
new_argument.gsub!("'", "\\\\'")
|
|
78
86
|
quote = "'"
|
|
@@ -82,6 +90,8 @@ module RuboCop
|
|
|
82
90
|
quote = enforce_double_quotes? ? '"' : "'"
|
|
83
91
|
end
|
|
84
92
|
|
|
93
|
+
new_argument = escape_interpolation_like_text(new_argument) if quote == '"'
|
|
94
|
+
|
|
85
95
|
"#{quote}#{new_argument}#{quote}"
|
|
86
96
|
end
|
|
87
97
|
|
|
@@ -101,6 +111,11 @@ module RuboCop
|
|
|
101
111
|
char
|
|
102
112
|
end.join
|
|
103
113
|
end
|
|
114
|
+
|
|
115
|
+
# `#{`, `#$` and `#@` would start an interpolation in a double-quoted string.
|
|
116
|
+
def escape_interpolation_like_text(string)
|
|
117
|
+
string.gsub(/#(?=[{$@])/) { '\#' }
|
|
118
|
+
end
|
|
104
119
|
end
|
|
105
120
|
end
|
|
106
121
|
end
|
|
@@ -74,7 +74,7 @@ module RuboCop
|
|
|
74
74
|
|
|
75
75
|
non_redundant =
|
|
76
76
|
whitespace_in_free_space_mode?(node, class_elem) ||
|
|
77
|
-
backslash_b?(class_elem) ||
|
|
77
|
+
backslash_b?(class_elem) || backreference_requiring_char_class?(class_elem) ||
|
|
78
78
|
requires_escape_outside_char_class?(class_elem)
|
|
79
79
|
|
|
80
80
|
!non_redundant
|
|
@@ -104,10 +104,11 @@ module RuboCop
|
|
|
104
104
|
elem == '\b'
|
|
105
105
|
end
|
|
106
106
|
|
|
107
|
-
def
|
|
108
|
-
#
|
|
109
|
-
#
|
|
110
|
-
|
|
107
|
+
def backreference_requiring_char_class?(elem)
|
|
108
|
+
# `\1` to `\9` only match a literal digit inside a character class;
|
|
109
|
+
# outside it they are backreferences (and a syntax error when the
|
|
110
|
+
# referenced group does not exist), so the class is not redundant.
|
|
111
|
+
elem.match?(/\A\\[1-9]\z/)
|
|
111
112
|
end
|
|
112
113
|
|
|
113
114
|
def requires_escape_outside_char_class?(elem)
|
|
@@ -3,8 +3,8 @@
|
|
|
3
3
|
module RuboCop
|
|
4
4
|
module Cop
|
|
5
5
|
module Style
|
|
6
|
-
# Checks for the instantiation of regexp using redundant `Regexp.new` or `Regexp.compile`.
|
|
7
|
-
# Autocorrect replaces
|
|
6
|
+
# Checks for the instantiation of a regexp using a redundant `Regexp.new` or `Regexp.compile`.
|
|
7
|
+
# Autocorrect replaces it with a regexp literal which is the simplest and fastest.
|
|
8
8
|
#
|
|
9
9
|
# @example
|
|
10
10
|
#
|
|
@@ -27,19 +27,39 @@ module RuboCop
|
|
|
27
27
|
def_node_matcher :redundant_regexp_constructor, <<~PATTERN
|
|
28
28
|
(send
|
|
29
29
|
(const {nil? cbase} :Regexp) {:new :compile}
|
|
30
|
-
(regexp
|
|
30
|
+
$(regexp _* (regopt _*)))
|
|
31
31
|
PATTERN
|
|
32
32
|
|
|
33
33
|
def on_send(node)
|
|
34
|
-
return unless (regexp
|
|
34
|
+
return unless (regexp = redundant_regexp_constructor(node))
|
|
35
35
|
|
|
36
36
|
add_offense(node, message: format(MSG, method: node.method_name)) do |corrector|
|
|
37
|
-
|
|
38
|
-
regopt = regopt.join
|
|
37
|
+
next if ambiguous_slash_regexp?(node, regexp)
|
|
39
38
|
|
|
40
|
-
|
|
39
|
+
# Reuse the inner literal's own source so its delimiters are preserved.
|
|
40
|
+
# Forcing `/.../` would break patterns like `%r{foo/bar}` that contain
|
|
41
|
+
# an unescaped slash.
|
|
42
|
+
corrector.replace(node, regexp.source)
|
|
41
43
|
end
|
|
42
44
|
end
|
|
45
|
+
|
|
46
|
+
private
|
|
47
|
+
|
|
48
|
+
# `p / a/` and `p /=a/` parse as division, so a slash regexp starting
|
|
49
|
+
# with whitespace or `=` can't begin the first argument of a command.
|
|
50
|
+
def ambiguous_slash_regexp?(node, regexp)
|
|
51
|
+
return false unless regexp.slash_literal? && regexp.content.match?(/\A[\s=]/)
|
|
52
|
+
|
|
53
|
+
begin_pos = node.source_range.begin_pos
|
|
54
|
+
|
|
55
|
+
node.each_ancestor(:call).any? do |call|
|
|
56
|
+
command?(call) && call.first_argument.source_range.begin_pos == begin_pos
|
|
57
|
+
end
|
|
58
|
+
end
|
|
59
|
+
|
|
60
|
+
def command?(call)
|
|
61
|
+
call.arguments? && !call.parenthesized? && !call.operator_method? && !call.setter_method?
|
|
62
|
+
end
|
|
43
63
|
end
|
|
44
64
|
end
|
|
45
65
|
end
|
|
@@ -41,6 +41,11 @@ module RuboCop
|
|
|
41
41
|
ALLOWED_ALWAYS_ESCAPES = " \n[]^\\#".chars.freeze
|
|
42
42
|
ALLOWED_WITHIN_CHAR_CLASS_METACHAR_ESCAPES = '-'.chars.freeze
|
|
43
43
|
ALLOWED_OUTSIDE_CHAR_CLASS_METACHAR_ESCAPES = '.*+?{}()|$'.chars.freeze
|
|
44
|
+
INTERPOLATION_SIGILS = %w[@ $].freeze
|
|
45
|
+
|
|
46
|
+
def self.autocorrect_incompatible_with
|
|
47
|
+
[Style::RegexpLiteral]
|
|
48
|
+
end
|
|
44
49
|
|
|
45
50
|
def on_regexp(node)
|
|
46
51
|
each_escape(node) do |char, index, within_character_class|
|
|
@@ -64,6 +69,7 @@ module RuboCop
|
|
|
64
69
|
# different versions of Ruby so that e.g. /\i/ != /i/
|
|
65
70
|
return true if /[[:alnum:]]/.match?(char)
|
|
66
71
|
return true if ALLOWED_ALWAYS_ESCAPES.include?(char) || delimiter?(node, char)
|
|
72
|
+
return true if requires_escape_to_avoid_interpolation?(node, index, char)
|
|
67
73
|
|
|
68
74
|
if within_character_class
|
|
69
75
|
ALLOWED_WITHIN_CHAR_CLASS_METACHAR_ESCAPES.include?(char) &&
|
|
@@ -95,6 +101,16 @@ module RuboCop
|
|
|
95
101
|
delimiters.include?(char)
|
|
96
102
|
end
|
|
97
103
|
|
|
104
|
+
def requires_escape_to_avoid_interpolation?(node, index, escaped_char)
|
|
105
|
+
# Preserve escapes after '#' that would otherwise trigger interpolation:
|
|
106
|
+
# '#@ivar', '#@@cvar', and '#$gvar'. `index` is relative to the regexp
|
|
107
|
+
# contents, so index into those rather than `node.source` (which also
|
|
108
|
+
# includes the opening delimiter, e.g. `%r{`).
|
|
109
|
+
return false unless index.positive? && INTERPOLATION_SIGILS.include?(escaped_char)
|
|
110
|
+
|
|
111
|
+
contents_range(node).source[index - 1] == '#'
|
|
112
|
+
end
|
|
113
|
+
|
|
98
114
|
def each_escape(node)
|
|
99
115
|
node.parsed_tree&.traverse&.reduce(0) do |char_class_depth, (event, expr)|
|
|
100
116
|
yield(expr.text[1], expr.ts, !char_class_depth.zero?) if expr.type == :escape
|
|
@@ -3,7 +3,9 @@
|
|
|
3
3
|
module RuboCop
|
|
4
4
|
module Cop
|
|
5
5
|
module Style
|
|
6
|
-
# Checks for redundant `return` expressions.
|
|
6
|
+
# Checks for redundant `return` expressions. Ruby methods
|
|
7
|
+
# implicitly return the value of the last evaluated expression,
|
|
8
|
+
# so an explicit `return` at the end of a method body is unnecessary.
|
|
7
9
|
#
|
|
8
10
|
# @example
|
|
9
11
|
# # These bad cases should be extended to handle methods whose body is
|
|
@@ -106,7 +108,7 @@ module RuboCop
|
|
|
106
108
|
corrector.insert_after(node.children.last, '}')
|
|
107
109
|
end
|
|
108
110
|
|
|
109
|
-
# rubocop:disable Metrics/CyclomaticComplexity
|
|
111
|
+
# rubocop:disable-next Metrics/CyclomaticComplexity
|
|
110
112
|
def check_branch(node)
|
|
111
113
|
return unless node
|
|
112
114
|
|
|
@@ -122,7 +124,6 @@ module RuboCop
|
|
|
122
124
|
check_begin_node(node)
|
|
123
125
|
end
|
|
124
126
|
end
|
|
125
|
-
# rubocop:enable Metrics/CyclomaticComplexity
|
|
126
127
|
|
|
127
128
|
def check_return_node(node)
|
|
128
129
|
return if cop_config['AllowMultipleReturnValues'] && node.children.size > 1
|
|
@@ -59,7 +59,7 @@ module RuboCop
|
|
|
59
59
|
|
|
60
60
|
def initialize(config = nil, options = nil)
|
|
61
61
|
super
|
|
62
|
-
@allowed_send_nodes =
|
|
62
|
+
@allowed_send_nodes = Set.new.compare_by_identity
|
|
63
63
|
@local_variables_scopes = Hash.new { |hash, key| hash[key] = [] }.compare_by_identity
|
|
64
64
|
end
|
|
65
65
|
|
|
@@ -67,6 +67,9 @@ module RuboCop
|
|
|
67
67
|
|
|
68
68
|
def on_or_asgn(node)
|
|
69
69
|
allow_self(node.lhs)
|
|
70
|
+
|
|
71
|
+
lhs_name = node.lhs.lvasgn_type? ? node.lhs.name : node.lhs
|
|
72
|
+
add_lhs_to_local_variables_scopes(node.rhs, lhs_name)
|
|
70
73
|
end
|
|
71
74
|
alias on_and_asgn on_or_asgn
|
|
72
75
|
|
|
@@ -97,6 +100,15 @@ module RuboCop
|
|
|
97
100
|
add_lhs_to_local_variables_scopes(node.rhs, node.lhs)
|
|
98
101
|
end
|
|
99
102
|
|
|
103
|
+
# Register the exception variable of `rescue => e` so that `self.e` in the
|
|
104
|
+
# body is not treated as redundant (it disambiguates the local variable).
|
|
105
|
+
def on_resbody(node)
|
|
106
|
+
exception_variable = node.exception_variable
|
|
107
|
+
return unless exception_variable&.lvasgn_type?
|
|
108
|
+
|
|
109
|
+
@local_variables_scopes[node] << exception_variable.name
|
|
110
|
+
end
|
|
111
|
+
|
|
100
112
|
def on_in_pattern(node)
|
|
101
113
|
add_match_var_scopes(node)
|
|
102
114
|
end
|
|
@@ -118,15 +130,16 @@ module RuboCop
|
|
|
118
130
|
end
|
|
119
131
|
|
|
120
132
|
alias on_numblock on_block
|
|
133
|
+
alias on_itblock on_block
|
|
121
134
|
|
|
122
135
|
def on_if(node)
|
|
123
136
|
# Allow conditional nodes to use `self` in the condition if that variable
|
|
124
137
|
# name is used in an `lvasgn` or `masgn` within the `if`.
|
|
125
|
-
node.
|
|
126
|
-
if
|
|
127
|
-
add_lhs_to_local_variables_scopes(node.condition,
|
|
128
|
-
|
|
129
|
-
add_masgn_lhs_variables(node.condition,
|
|
138
|
+
node.each_descendant(:lvasgn, :masgn) do |descendant_node|
|
|
139
|
+
if descendant_node.lvasgn_type?
|
|
140
|
+
add_lhs_to_local_variables_scopes(node.condition, descendant_node.lhs)
|
|
141
|
+
else
|
|
142
|
+
add_masgn_lhs_variables(node.condition, descendant_node.lhs)
|
|
130
143
|
end
|
|
131
144
|
end
|
|
132
145
|
end
|
|
@@ -183,7 +196,7 @@ module RuboCop
|
|
|
183
196
|
def allow_self(node)
|
|
184
197
|
return unless node.send_type? && node.self_receiver?
|
|
185
198
|
|
|
186
|
-
@allowed_send_nodes
|
|
199
|
+
@allowed_send_nodes.add(node)
|
|
187
200
|
end
|
|
188
201
|
|
|
189
202
|
def add_lhs_to_local_variables_scopes(rhs, lhs)
|