rubocop 1.81.7 → 1.92.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/LICENSE.txt +1 -1
- data/README.md +2 -2
- data/config/default.yml +626 -111
- data/config/obsoletion.yml +39 -1
- data/exe/rubocop +1 -1
- 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 +34 -2
- 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 +1 -1
- data/lib/rubocop/cli.rb +41 -14
- 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 +97 -44
- data/lib/rubocop/config.rb +100 -15
- data/lib/rubocop/config_finder.rb +1 -1
- data/lib/rubocop/config_loader.rb +49 -27
- data/lib/rubocop/config_loader_resolver.rb +95 -20
- data/lib/rubocop/config_obsoletion/cop_rule.rb +2 -1
- data/lib/rubocop/config_obsoletion/extracted_cop.rb +4 -2
- data/lib/rubocop/config_obsoletion/removed_cop.rb +9 -1
- data/lib/rubocop/config_obsoletion.rb +1 -1
- data/lib/rubocop/config_store.rb +2 -2
- data/lib/rubocop/config_validator.rb +69 -7
- data/lib/rubocop/cop/autocorrect_logic.rb +24 -6
- data/lib/rubocop/cop/badge.rb +10 -2
- 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 +1 -10
- 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 +87 -9
- data/lib/rubocop/cop/correctors/condition_corrector.rb +1 -1
- data/lib/rubocop/cop/correctors/each_to_for_corrector.rb +37 -7
- data/lib/rubocop/cop/correctors/empty_line_corrector.rb +1 -1
- data/lib/rubocop/cop/correctors/lambda_literal_to_method_corrector.rb +31 -4
- data/lib/rubocop/cop/correctors/multiline_literal_brace_corrector.rb +35 -5
- data/lib/rubocop/cop/correctors/ordered_gem_corrector.rb +8 -1
- data/lib/rubocop/cop/correctors/parentheses_corrector.rb +70 -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/dependency_version.rb +0 -6
- data/lib/rubocop/cop/gemspec/development_dependencies.rb +1 -1
- data/lib/rubocop/cop/gemspec/duplicated_assignment.rb +14 -4
- data/lib/rubocop/cop/gemspec/ordered_dependencies.rb +1 -8
- data/lib/rubocop/cop/gemspec/require_mfa.rb +9 -6
- 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_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 +28 -2
- data/lib/rubocop/cop/internal_affairs/location_line_equality_comparison.rb +1 -0
- data/lib/rubocop/cop/internal_affairs/node_matcher_directive.rb +12 -16
- 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_type_group.rb +0 -7
- data/lib/rubocop/cop/internal_affairs/on_send_without_on_csend.rb +1 -1
- data/lib/rubocop/cop/internal_affairs/redundant_context_config_parameter.rb +1 -7
- 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/useless_message_assertion.rb +4 -4
- data/lib/rubocop/cop/internal_affairs.rb +1 -0
- data/lib/rubocop/cop/layout/argument_alignment.rb +9 -3
- 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 +84 -4
- data/lib/rubocop/cop/layout/case_indentation.rb +28 -10
- data/lib/rubocop/cop/layout/class_structure.rb +156 -41
- 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 +4 -0
- data/lib/rubocop/cop/layout/dot_position.rb +26 -16
- data/lib/rubocop/cop/layout/else_alignment.rb +2 -14
- data/lib/rubocop/cop/layout/empty_comment.rb +8 -10
- data/lib/rubocop/cop/layout/empty_line_after_guard_clause.rb +25 -7
- data/lib/rubocop/cop/layout/empty_line_after_magic_comment.rb +63 -5
- data/lib/rubocop/cop/layout/empty_line_after_multiline_condition.rb +21 -8
- data/lib/rubocop/cop/layout/empty_line_between_defs.rb +15 -2
- data/lib/rubocop/cop/layout/empty_lines.rb +5 -2
- data/lib/rubocop/cop/layout/empty_lines_after_module_inclusion.rb +2 -2
- data/lib/rubocop/cop/layout/empty_lines_around_attribute_accessor.rb +2 -0
- data/lib/rubocop/cop/layout/empty_lines_around_block_body.rb +21 -5
- data/lib/rubocop/cop/layout/empty_lines_around_class_body.rb +16 -2
- data/lib/rubocop/cop/layout/empty_lines_around_exception_handling_keywords.rb +23 -1
- data/lib/rubocop/cop/layout/empty_lines_around_module_body.rb +16 -2
- data/lib/rubocop/cop/layout/end_alignment.rb +23 -15
- data/lib/rubocop/cop/layout/extra_spacing.rb +109 -3
- data/lib/rubocop/cop/layout/first_argument_indentation.rb +81 -2
- data/lib/rubocop/cop/layout/first_array_element_indentation.rb +18 -5
- data/lib/rubocop/cop/layout/first_array_element_line_break.rb +41 -0
- data/lib/rubocop/cop/layout/first_hash_element_indentation.rb +36 -23
- 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 +16 -11
- data/lib/rubocop/cop/layout/heredoc_argument_closing_parenthesis.rb +8 -4
- data/lib/rubocop/cop/layout/heredoc_indentation.rb +48 -3
- data/lib/rubocop/cop/layout/indentation_consistency.rb +22 -5
- data/lib/rubocop/cop/layout/indentation_style.rb +5 -2
- data/lib/rubocop/cop/layout/indentation_width.rb +158 -12
- data/lib/rubocop/cop/layout/leading_comment_space.rb +27 -0
- 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 +265 -29
- 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 +10 -1
- data/lib/rubocop/cop/layout/multiline_hash_brace_layout.rb +65 -56
- data/lib/rubocop/cop/layout/multiline_method_call_brace_layout.rb +7 -1
- data/lib/rubocop/cop/layout/multiline_method_call_indentation.rb +268 -38
- data/lib/rubocop/cop/layout/multiline_method_definition_brace_layout.rb +4 -0
- data/lib/rubocop/cop/layout/parameter_alignment.rb +1 -1
- data/lib/rubocop/cop/layout/redundant_line_break.rb +102 -2
- data/lib/rubocop/cop/layout/rescue_ensure_alignment.rb +19 -5
- 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 +1 -1
- data/lib/rubocop/cop/layout/space_around_block_parameters.rb +10 -4
- data/lib/rubocop/cop/layout/space_around_keyword.rb +14 -2
- data/lib/rubocop/cop/layout/space_around_operators.rb +18 -3
- data/lib/rubocop/cop/layout/space_before_block_braces.rb +4 -1
- data/lib/rubocop/cop/layout/space_before_brackets.rb +1 -1
- data/lib/rubocop/cop/layout/space_in_lambda_literal.rb +9 -8
- data/lib/rubocop/cop/layout/space_inside_array_literal_brackets.rb +44 -34
- data/lib/rubocop/cop/layout/space_inside_block_braces.rb +31 -8
- data/lib/rubocop/cop/layout/space_inside_reference_brackets.rb +2 -12
- 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 +1 -2
- data/lib/rubocop/cop/lint/ambiguous_regexp_literal.rb +6 -1
- data/lib/rubocop/cop/lint/argument_mismatch.rb +99 -0
- data/lib/rubocop/cop/lint/assignment_in_condition.rb +15 -1
- data/lib/rubocop/cop/lint/circular_argument_reference.rb +45 -3
- data/lib/rubocop/cop/lint/constant_overwritten_in_rescue.rb +1 -1
- 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 +165 -15
- data/lib/rubocop/cop/lint/data_define_override.rb +63 -0
- data/lib/rubocop/cop/lint/debugger.rb +13 -2
- data/lib/rubocop/cop/lint/deprecated_constants.rb +2 -8
- 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 +405 -28
- 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 +9 -2
- data/lib/rubocop/cop/lint/empty_in_pattern.rb +8 -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 -2
- data/lib/rubocop/cop/lint/float_comparison.rb +2 -1
- data/lib/rubocop/cop/lint/heredoc_method_call_position.rb +4 -0
- 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 +36 -9
- 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 +46 -18
- data/lib/rubocop/cop/lint/missing_super.rb +31 -1
- 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 +1 -1
- 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 +1 -1
- data/lib/rubocop/cop/lint/number_conversion.rb +22 -11
- data/lib/rubocop/cop/lint/numbered_parameter_assignment.rb +1 -1
- data/lib/rubocop/cop/lint/numeric_operation_with_constant_result.rb +10 -0
- 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 +1 -1
- 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_require_statement.rb +5 -4
- data/lib/rubocop/cop/lint/redundant_safe_navigation.rb +37 -14
- data/lib/rubocop/cop/lint/redundant_splat_expansion.rb +13 -4
- data/lib/rubocop/cop/lint/redundant_type_conversion.rb +11 -5
- data/lib/rubocop/cop/lint/redundant_with_index.rb +2 -3
- data/lib/rubocop/cop/lint/redundant_with_object.rb +5 -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 +2 -1
- data/lib/rubocop/cop/lint/require_relative_self_path.rb +7 -5
- data/lib/rubocop/cop/lint/rescue_type.rb +1 -1
- data/lib/rubocop/cop/lint/safe_navigation_chain.rb +24 -0
- data/lib/rubocop/cop/lint/safe_navigation_consistency.rb +56 -6
- 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 +33 -2
- data/lib/rubocop/cop/lint/send_with_mixin_argument.rb +1 -1
- data/lib/rubocop/cop/lint/shadowed_exception.rb +1 -1
- data/lib/rubocop/cop/lint/shadowing_outer_local_variable.rb +14 -0
- data/lib/rubocop/cop/lint/shared_mutable_default.rb +3 -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_in_number_conversion.rb +13 -2
- data/lib/rubocop/cop/lint/symbol_conversion.rb +22 -4
- data/lib/rubocop/cop/lint/syntax.rb +25 -1
- data/lib/rubocop/cop/lint/to_enum_arguments.rb +72 -4
- 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/unmodified_reduce_accumulator.rb +1 -0
- data/lib/rubocop/cop/lint/unreachable_code.rb +15 -9
- 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/useless_access_modifier.rb +1 -2
- data/lib/rubocop/cop/lint/useless_assignment.rb +61 -27
- data/lib/rubocop/cop/lint/useless_constant_scoping.rb +40 -4
- data/lib/rubocop/cop/lint/useless_default_value_argument.rb +2 -0
- data/lib/rubocop/cop/lint/useless_method_definition.rb +1 -1
- data/lib/rubocop/cop/lint/useless_numeric_operation.rb +10 -10
- data/lib/rubocop/cop/lint/useless_or.rb +15 -2
- data/lib/rubocop/cop/lint/useless_rescue.rb +1 -2
- data/lib/rubocop/cop/lint/useless_ruby2_keywords.rb +10 -4
- data/lib/rubocop/cop/lint/useless_setter_call.rb +11 -5
- data/lib/rubocop/cop/lint/useless_times.rb +22 -1
- data/lib/rubocop/cop/lint/utils/nil_receiver_checker.rb +94 -14
- data/lib/rubocop/cop/lint/void.rb +59 -22
- data/lib/rubocop/cop/lint.rb +179 -0
- data/lib/rubocop/cop/metrics/block_length.rb +1 -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 +2 -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 +1 -1
- data/lib/rubocop/cop/metrics/utils/iterating_block.rb +1 -1
- 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 +5 -1
- data/lib/rubocop/cop/mixin/allowed_methods.rb +5 -5
- data/lib/rubocop/cop/mixin/allowed_pattern.rb +5 -1
- data/lib/rubocop/cop/mixin/annotation_comment.rb +1 -1
- data/lib/rubocop/cop/mixin/check_line_breakable.rb +47 -25
- data/lib/rubocop/cop/mixin/check_single_line_suitability.rb +12 -8
- data/lib/rubocop/cop/mixin/code_length.rb +10 -2
- data/lib/rubocop/cop/mixin/comments_help.rb +1 -2
- 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/empty_lines_around_body.rb +12 -1
- data/lib/rubocop/cop/mixin/endless_method_body_help.rb +105 -0
- data/lib/rubocop/cop/mixin/endless_method_rewriter.rb +13 -5
- data/lib/rubocop/cop/mixin/forbidden_identifiers.rb +2 -2
- data/lib/rubocop/cop/mixin/forbidden_pattern.rb +5 -1
- data/lib/rubocop/cop/mixin/hash_alignment_styles.rb +58 -12
- data/lib/rubocop/cop/mixin/hash_shorthand_syntax.rb +37 -10
- data/lib/rubocop/cop/mixin/hash_subset.rb +9 -2
- data/lib/rubocop/cop/mixin/hash_transform_method/autocorrection.rb +63 -0
- data/lib/rubocop/cop/mixin/hash_transform_method.rb +14 -60
- data/lib/rubocop/cop/mixin/indexed_method_arity.rb +94 -0
- data/lib/rubocop/cop/mixin/line_length_help.rb +28 -3
- data/lib/rubocop/cop/mixin/method_complexity.rb +1 -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 +1 -1
- data/lib/rubocop/cop/mixin/multiline_literal_brace_layout.rb +10 -1
- data/lib/rubocop/cop/mixin/ordered_gem_node.rb +1 -1
- data/lib/rubocop/cop/mixin/pattern_matching_help.rb +35 -0
- 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 +1 -2
- 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 +69 -12
- data/lib/rubocop/cop/mixin/trailing_comma.rb +7 -6
- data/lib/rubocop/cop/mixin/visibility_help.rb +2 -1
- 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 +4 -1
- data/lib/rubocop/cop/naming/block_parameter_name.rb +1 -1
- data/lib/rubocop/cop/naming/file_name.rb +4 -3
- 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 +12 -5
- data/lib/rubocop/cop/naming/method_name.rb +6 -3
- data/lib/rubocop/cop/naming/predicate_method.rb +13 -2
- data/lib/rubocop/cop/naming/predicate_prefix.rb +30 -17
- data/lib/rubocop/cop/naming/rescued_exceptions_variable_name.rb +12 -7
- 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 +232 -66
- data/lib/rubocop/cop/security/eval.rb +15 -2
- data/lib/rubocop/cop/security/io_methods.rb +2 -2
- data/lib/rubocop/cop/security/json_load.rb +16 -4
- data/lib/rubocop/cop/security/marshal_load.rb +1 -1
- 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 +55 -8
- data/lib/rubocop/cop/style/accessor_grouping.rb +16 -5
- 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 +8 -3
- data/lib/rubocop/cop/style/arguments_forwarding.rb +61 -17
- data/lib/rubocop/cop/style/array_first_last.rb +13 -3
- data/lib/rubocop/cop/style/array_intersect.rb +28 -5
- data/lib/rubocop/cop/style/array_intersect_with_single_element.rb +3 -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 +7 -6
- data/lib/rubocop/cop/style/block_delimiters.rb +74 -38
- data/lib/rubocop/cop/style/case_equality.rb +29 -15
- data/lib/rubocop/cop/style/case_like_if.rb +11 -10
- data/lib/rubocop/cop/style/character_literal.rb +2 -2
- data/lib/rubocop/cop/style/class_and_module_children.rb +151 -35
- data/lib/rubocop/cop/style/class_equality_comparison.rb +21 -13
- data/lib/rubocop/cop/style/class_methods_definitions.rb +26 -5
- data/lib/rubocop/cop/style/collection_compact.rb +37 -17
- data/lib/rubocop/cop/style/collection_querying.rb +79 -46
- data/lib/rubocop/cop/style/colon_method_call.rb +16 -7
- data/lib/rubocop/cop/style/combinable_loops.rb +91 -9
- data/lib/rubocop/cop/style/comparable_clamp.rb +12 -1
- data/lib/rubocop/cop/style/concat_array_literals.rb +65 -9
- data/lib/rubocop/cop/style/conditional_assignment.rb +34 -18
- data/lib/rubocop/cop/style/constant_visibility.rb +13 -7
- data/lib/rubocop/cop/style/copyright.rb +27 -12
- data/lib/rubocop/cop/style/data_inheritance.rb +18 -0
- data/lib/rubocop/cop/style/date_time.rb +4 -4
- data/lib/rubocop/cop/style/def_with_parentheses.rb +6 -2
- data/lib/rubocop/cop/style/dig_chain.rb +5 -0
- 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 +11 -0
- data/lib/rubocop/cop/style/each_for_simple_loop.rb +1 -1
- data/lib/rubocop/cop/style/each_with_object.rb +2 -0
- 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 +8 -3
- data/lib/rubocop/cop/style/empty_method.rb +15 -9
- data/lib/rubocop/cop/style/empty_string_inside_interpolation.rb +74 -22
- 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 +100 -21
- data/lib/rubocop/cop/style/env_home.rb +4 -0
- 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/explicit_block_argument.rb +50 -10
- data/lib/rubocop/cop/style/fetch_env_var.rb +1 -1
- 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 +28 -14
- data/lib/rubocop/cop/style/for.rb +60 -1
- data/lib/rubocop/cop/style/format_string.rb +44 -9
- data/lib/rubocop/cop/style/format_string_token.rb +50 -7
- data/lib/rubocop/cop/style/frozen_string_literal_comment.rb +2 -1
- data/lib/rubocop/cop/style/global_vars.rb +5 -2
- data/lib/rubocop/cop/style/guard_clause.rb +57 -40
- data/lib/rubocop/cop/style/hash_as_last_array_item.rb +31 -9
- data/lib/rubocop/cop/style/hash_conversion.rb +39 -11
- data/lib/rubocop/cop/style/hash_each_methods.rb +1 -2
- 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 +19 -5
- data/lib/rubocop/cop/style/hash_transform_keys.rb +17 -7
- data/lib/rubocop/cop/style/hash_transform_values.rb +17 -7
- data/lib/rubocop/cop/style/identical_conditional_branches.rb +38 -10
- data/lib/rubocop/cop/style/if_inside_else.rb +36 -8
- data/lib/rubocop/cop/style/if_unless_modifier.rb +80 -76
- data/lib/rubocop/cop/style/if_unless_modifier_of_if_unless.rb +17 -14
- data/lib/rubocop/cop/style/if_with_boolean_literal_branches.rb +4 -1
- data/lib/rubocop/cop/style/if_with_semicolon.rb +61 -8
- data/lib/rubocop/cop/style/inline_comment.rb +5 -2
- data/lib/rubocop/cop/style/inverse_methods.rb +24 -2
- data/lib/rubocop/cop/style/invertible_unless_condition.rb +25 -5
- data/lib/rubocop/cop/style/ip_addresses.rb +1 -2
- data/lib/rubocop/cop/style/it_block_parameter.rb +94 -4
- data/lib/rubocop/cop/style/keyword_arguments_merging.rb +4 -0
- data/lib/rubocop/cop/style/keyword_parameters_order.rb +10 -4
- data/lib/rubocop/cop/style/lambda.rb +45 -2
- data/lib/rubocop/cop/style/lambda_call.rb +24 -8
- 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 +2 -3
- data/lib/rubocop/cop/style/map_join.rb +123 -0
- data/lib/rubocop/cop/style/map_to_hash.rb +1 -2
- data/lib/rubocop/cop/style/method_call_with_args_parentheses/omit_parentheses.rb +102 -20
- 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 +42 -6
- data/lib/rubocop/cop/style/method_call_without_args_parentheses.rb +36 -8
- data/lib/rubocop/cop/style/method_def_parentheses.rb +36 -8
- data/lib/rubocop/cop/style/min_max_comparison.rb +4 -1
- 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_grouping.rb +12 -3
- 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_if_modifier.rb +45 -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 +14 -13
- 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 +158 -14
- 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 +24 -10
- data/lib/rubocop/cop/style/nil_comparison.rb +50 -12
- 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/one_class_per_file.rb +115 -0
- data/lib/rubocop/cop/style/one_line_conditional.rb +18 -6
- 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 +26 -7
- data/lib/rubocop/cop/style/parentheses_around_condition.rb +7 -2
- 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/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 +3 -2
- data/lib/rubocop/cop/style/raise_args.rb +20 -10
- 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_assignment.rb +12 -2
- data/lib/rubocop/cop/style/redundant_begin.rb +25 -7
- data/lib/rubocop/cop/style/redundant_condition.rb +41 -23
- data/lib/rubocop/cop/style/redundant_constant_base.rb +42 -6
- data/lib/rubocop/cop/style/redundant_current_directory_in_path.rb +13 -1
- 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 +21 -3
- data/lib/rubocop/cop/style/redundant_fetch_block.rb +10 -2
- 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 +43 -7
- data/lib/rubocop/cop/style/redundant_freeze.rb +11 -3
- data/lib/rubocop/cop/style/redundant_heredoc_delimiter_quotes.rb +6 -1
- data/lib/rubocop/cop/style/redundant_interpolation_unfreeze.rb +49 -10
- data/lib/rubocop/cop/style/redundant_line_continuation.rb +82 -115
- data/lib/rubocop/cop/style/redundant_min_max_by.rb +93 -0
- data/lib/rubocop/cop/style/redundant_parentheses.rb +105 -83
- data/lib/rubocop/cop/style/redundant_percent_q.rb +5 -3
- data/lib/rubocop/cop/style/redundant_regexp_argument.rb +13 -2
- 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 +12 -4
- data/lib/rubocop/cop/style/redundant_return.rb +4 -3
- data/lib/rubocop/cop/style/redundant_self.rb +11 -2
- data/lib/rubocop/cop/style/redundant_self_assignment.rb +1 -2
- data/lib/rubocop/cop/style/redundant_self_assignment_branch.rb +27 -4
- data/lib/rubocop/cop/style/redundant_sort.rb +45 -11
- 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 +106 -28
- data/lib/rubocop/cop/style/require_order.rb +25 -8
- data/lib/rubocop/cop/style/rescue_modifier.rb +15 -14
- data/lib/rubocop/cop/style/return_nil.rb +17 -2
- 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 +18 -9
- 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 +52 -23
- data/lib/rubocop/cop/style/self_assignment.rb +13 -16
- data/lib/rubocop/cop/style/semicolon.rb +39 -13
- data/lib/rubocop/cop/style/send_with_literal_method_name.rb +4 -0
- data/lib/rubocop/cop/style/single_line_block_params.rb +2 -2
- data/lib/rubocop/cop/style/single_line_do_end_block.rb +19 -7
- data/lib/rubocop/cop/style/single_line_methods.rb +24 -5
- data/lib/rubocop/cop/style/sole_nested_conditional.rb +25 -7
- data/lib/rubocop/cop/style/special_global_vars.rb +7 -2
- data/lib/rubocop/cop/style/stabby_lambda_parentheses.rb +31 -5
- data/lib/rubocop/cop/style/static_class.rb +21 -0
- data/lib/rubocop/cop/style/string_concatenation.rb +25 -6
- data/lib/rubocop/cop/style/string_hash_keys.rb +1 -0
- data/lib/rubocop/cop/style/struct_inheritance.rb +36 -1
- data/lib/rubocop/cop/style/super_arguments.rb +6 -4
- data/lib/rubocop/cop/style/symbol_proc.rb +32 -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 +2 -2
- data/lib/rubocop/cop/style/trailing_comma_in_block_args.rb +1 -1
- 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 +1 -1
- 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 -0
- 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 +171 -48
- data/lib/rubocop/cop/util.rb +5 -8
- data/lib/rubocop/cop/variable_force/assignment.rb +1 -1
- data/lib/rubocop/cop/variable_force/branch.rb +30 -6
- data/lib/rubocop/cop/variable_force/variable.rb +33 -9
- data/lib/rubocop/cops_documentation_generator.rb +27 -9
- data/lib/rubocop/directive_comment.rb +116 -7
- 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 +39 -10
- data/lib/rubocop/formatter/emacs_style_formatter.rb +3 -1
- data/lib/rubocop/formatter/formatter_set.rb +7 -2
- data/lib/rubocop/formatter/github_actions_formatter.rb +6 -5
- data/lib/rubocop/formatter/html_formatter.rb +2 -4
- data/lib/rubocop/formatter/json_formatter.rb +82 -7
- data/lib/rubocop/formatter/junit_formatter.rb +27 -10
- data/lib/rubocop/formatter/offense_count_formatter.rb +4 -3
- data/lib/rubocop/formatter/pacman_formatter.rb +3 -1
- 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 -42
- data/lib/rubocop/lsp/disable_comment_edits.rb +135 -0
- data/lib/rubocop/lsp/routes.rb +130 -83
- data/lib/rubocop/lsp/runtime.rb +64 -15
- data/lib/rubocop/lsp/server.rb +6 -2
- data/lib/rubocop/lsp/stdin_runner.rb +35 -2
- data/lib/rubocop/lsp.rb +5 -2
- data/lib/rubocop/magic_comment.rb +47 -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 +141 -13
- data/lib/rubocop/path_util.rb +16 -5
- data/lib/rubocop/pending_cops_reporter.rb +1 -6
- data/lib/rubocop/plugin/configuration_integrator.rb +13 -3
- data/lib/rubocop/plugin/loader.rb +2 -2
- data/lib/rubocop/project_index_loader.rb +82 -0
- data/lib/rubocop/rake_task.rb +2 -3
- data/lib/rubocop/remote_config.rb +18 -13
- data/lib/rubocop/result_cache.rb +102 -59
- data/lib/rubocop/rspec/cop_helper.rb +8 -0
- data/lib/rubocop/rspec/expect_offense.rb +2 -4
- data/lib/rubocop/rspec/shared_contexts.rb +53 -5
- data/lib/rubocop/rspec/support.rb +2 -1
- data/lib/rubocop/runner.rb +362 -106
- data/lib/rubocop/server/cache.rb +21 -40
- data/lib/rubocop/server/cli.rb +2 -4
- data/lib/rubocop/server/core.rb +8 -0
- data/lib/rubocop/server.rb +14 -0
- data/lib/rubocop/target_finder.rb +18 -8
- data/lib/rubocop/target_ruby.rb +42 -22
- 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 +23 -7
- data/lib/rubocop.rb +34 -701
- data/lib/ruby_lsp/rubocop/addon.rb +1 -2
- metadata +80 -14
- data/lib/rubocop/cop/style/double_cop_disable_directive.rb +0 -46
|
@@ -0,0 +1,216 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module RuboCop
|
|
4
|
+
module Cop
|
|
5
|
+
module Style
|
|
6
|
+
# Checks for `each_with_object`, `inject`, and `reduce` calls that build
|
|
7
|
+
# a hash from an enumerable, where `to_h` with a block could be used instead.
|
|
8
|
+
#
|
|
9
|
+
# This cop complements `Style/HashTransformKeys` and `Style/HashTransformValues`,
|
|
10
|
+
# which handle hash-to-hash transformations with destructured key-value pairs.
|
|
11
|
+
# This cop targets the case where a hash is built from individual elements
|
|
12
|
+
# (non-destructured block parameter).
|
|
13
|
+
#
|
|
14
|
+
# @safety
|
|
15
|
+
# This cop is unsafe because it cannot guarantee that the receiver
|
|
16
|
+
# is an `Enumerable` by static analysis, so the correction may
|
|
17
|
+
# not be actually equivalent. Additionally, `each_with_object` returns
|
|
18
|
+
# the hash object while `to_h` returns a new hash, which could matter
|
|
19
|
+
# if the hash object identity is important.
|
|
20
|
+
#
|
|
21
|
+
# @example
|
|
22
|
+
# # bad
|
|
23
|
+
# array.each_with_object({}) { |elem, hash| hash[elem.id] = elem.name }
|
|
24
|
+
#
|
|
25
|
+
# # bad
|
|
26
|
+
# array.inject({}) { |hash, elem| hash[elem.id] = elem.name; hash }
|
|
27
|
+
#
|
|
28
|
+
# # bad
|
|
29
|
+
# array.reduce({}) { |hash, elem| hash[elem.id] = elem.name; hash }
|
|
30
|
+
#
|
|
31
|
+
# # bad
|
|
32
|
+
# array.each_with_object({}) { |elem, hash| hash[elem] = elem.to_s }
|
|
33
|
+
#
|
|
34
|
+
# # good
|
|
35
|
+
# array.to_h { |elem| [elem.id, elem.name] }
|
|
36
|
+
#
|
|
37
|
+
# # good
|
|
38
|
+
# array.to_h { |elem| [elem, elem.to_s] }
|
|
39
|
+
#
|
|
40
|
+
class ReduceToHash < Base
|
|
41
|
+
extend AutoCorrector
|
|
42
|
+
extend TargetRubyVersion
|
|
43
|
+
include RangeHelp
|
|
44
|
+
|
|
45
|
+
minimum_target_ruby_version 2.6
|
|
46
|
+
|
|
47
|
+
MSG = 'Use `to_h { ... }` instead of `%<method>s`.'
|
|
48
|
+
RESTRICT_ON_SEND = %i[each_with_object inject reduce].freeze
|
|
49
|
+
|
|
50
|
+
# each_with_object({}) { |elem, hash| hash[key] = value }
|
|
51
|
+
# @!method each_with_object_to_hash?(node)
|
|
52
|
+
def_node_matcher :each_with_object_to_hash?, <<~PATTERN
|
|
53
|
+
{
|
|
54
|
+
(block
|
|
55
|
+
(call _ :each_with_object (hash))
|
|
56
|
+
(args (arg _elem) (arg _hash))
|
|
57
|
+
(send (lvar _hash) :[]= $_key $_value))
|
|
58
|
+
(numblock
|
|
59
|
+
(call _ :each_with_object (hash))
|
|
60
|
+
2
|
|
61
|
+
(send (lvar :_2) :[]= $_key $_value))
|
|
62
|
+
}
|
|
63
|
+
PATTERN
|
|
64
|
+
|
|
65
|
+
# inject/reduce({}) { |hash, elem| hash[key] = value; hash }
|
|
66
|
+
# @!method inject_to_hash?(node)
|
|
67
|
+
def_node_matcher :inject_to_hash?, <<~PATTERN
|
|
68
|
+
{
|
|
69
|
+
(block
|
|
70
|
+
(call _ {:inject :reduce} (hash))
|
|
71
|
+
(args (arg _hash) (arg _elem))
|
|
72
|
+
(begin
|
|
73
|
+
(send (lvar _hash) :[]= $_key $_value)
|
|
74
|
+
(lvar _hash)))
|
|
75
|
+
(numblock
|
|
76
|
+
(call _ {:inject :reduce} (hash))
|
|
77
|
+
2
|
|
78
|
+
(begin
|
|
79
|
+
(send (lvar :_1) :[]= $_key $_value)
|
|
80
|
+
(lvar :_1)))
|
|
81
|
+
}
|
|
82
|
+
PATTERN
|
|
83
|
+
|
|
84
|
+
def on_send(node)
|
|
85
|
+
block_node = node.block_node
|
|
86
|
+
return unless block_node
|
|
87
|
+
|
|
88
|
+
check_offense(node, block_node)
|
|
89
|
+
end
|
|
90
|
+
alias on_csend on_send
|
|
91
|
+
|
|
92
|
+
private
|
|
93
|
+
|
|
94
|
+
def check_offense(node, block_node)
|
|
95
|
+
key, value = if node.method?(:each_with_object)
|
|
96
|
+
each_with_object_to_hash?(block_node)
|
|
97
|
+
else
|
|
98
|
+
inject_to_hash?(block_node)
|
|
99
|
+
end
|
|
100
|
+
return unless key
|
|
101
|
+
return if accumulator_used_in_expressions?(block_node, key, value)
|
|
102
|
+
return if nested_match?(key) || nested_match?(value)
|
|
103
|
+
|
|
104
|
+
register_offense(node, block_node, key, value)
|
|
105
|
+
end
|
|
106
|
+
|
|
107
|
+
def accumulator_used_in_expressions?(block_node, key, value)
|
|
108
|
+
acc_name = accumulator_name(block_node)
|
|
109
|
+
references_variable?(key, acc_name) || references_variable?(value, acc_name)
|
|
110
|
+
end
|
|
111
|
+
|
|
112
|
+
def nested_match?(node)
|
|
113
|
+
node.each_node(:call).any? do |send_node|
|
|
114
|
+
next false unless RESTRICT_ON_SEND.include?(send_node.method_name)
|
|
115
|
+
|
|
116
|
+
inner_block = send_node.block_node
|
|
117
|
+
next false unless inner_block
|
|
118
|
+
|
|
119
|
+
if send_node.method?(:each_with_object)
|
|
120
|
+
each_with_object_to_hash?(inner_block)
|
|
121
|
+
else
|
|
122
|
+
inject_to_hash?(inner_block)
|
|
123
|
+
end
|
|
124
|
+
end
|
|
125
|
+
end
|
|
126
|
+
|
|
127
|
+
def accumulator_name(block_node)
|
|
128
|
+
index = block_node.method?(:each_with_object) ? 1 : 0
|
|
129
|
+
block_node.argument_list[index].name
|
|
130
|
+
end
|
|
131
|
+
|
|
132
|
+
def references_variable?(node, name)
|
|
133
|
+
node.each_node(:lvar).any? { |lvar| lvar.children.first == name }
|
|
134
|
+
end
|
|
135
|
+
|
|
136
|
+
def register_offense(send_node, block_node, key_expr, value_expr)
|
|
137
|
+
message = format(MSG, method: send_node.method_name)
|
|
138
|
+
|
|
139
|
+
add_offense(send_node.loc.selector, message: message) do |corrector|
|
|
140
|
+
corrector.replace(
|
|
141
|
+
replacement_range(send_node, block_node),
|
|
142
|
+
replacement(block_node, key_expr, value_expr)
|
|
143
|
+
)
|
|
144
|
+
end
|
|
145
|
+
end
|
|
146
|
+
|
|
147
|
+
def replacement(block_node, key_expr, value_expr)
|
|
148
|
+
key_source = adjusted_source(key_expr, block_node)
|
|
149
|
+
value_source = adjusted_source(value_expr, block_node)
|
|
150
|
+
body = "[#{key_source}, #{value_source}]"
|
|
151
|
+
|
|
152
|
+
if block_node.numblock_type?
|
|
153
|
+
block_node.braces? ? "to_h { #{body} }" : do_end_replacement(block_node, body)
|
|
154
|
+
else
|
|
155
|
+
named_block_replacement(block_node, body)
|
|
156
|
+
end
|
|
157
|
+
end
|
|
158
|
+
|
|
159
|
+
def named_block_replacement(block_node, body)
|
|
160
|
+
arg = element_arg_source(block_node)
|
|
161
|
+
if block_node.braces?
|
|
162
|
+
"to_h { |#{arg}| #{body} }"
|
|
163
|
+
else
|
|
164
|
+
do_end_replacement(block_node, body, arg)
|
|
165
|
+
end
|
|
166
|
+
end
|
|
167
|
+
|
|
168
|
+
def do_end_replacement(block_node, body, arg = nil)
|
|
169
|
+
args = arg ? " |#{arg}|" : ''
|
|
170
|
+
"to_h do#{args}\n#{indent(block_node)} #{body}\n#{indent(block_node)}end"
|
|
171
|
+
end
|
|
172
|
+
|
|
173
|
+
def replacement_range(send_node, block_node)
|
|
174
|
+
range_between(send_node.loc.selector.begin_pos, block_node.source_range.end_pos)
|
|
175
|
+
end
|
|
176
|
+
|
|
177
|
+
def element_arg_source(block_node)
|
|
178
|
+
if block_node.method?(:each_with_object)
|
|
179
|
+
block_node.first_argument.source
|
|
180
|
+
else
|
|
181
|
+
block_node.arguments[1].source
|
|
182
|
+
end
|
|
183
|
+
end
|
|
184
|
+
|
|
185
|
+
def adjusted_source(expr_node, block_node)
|
|
186
|
+
source = element_source(expr_node)
|
|
187
|
+
return source unless block_node.numblock_type?
|
|
188
|
+
return source if block_node.method?(:each_with_object)
|
|
189
|
+
|
|
190
|
+
# For inject/reduce numblocks, _2 is the element (becomes _1)
|
|
191
|
+
source.gsub('_2', '_1')
|
|
192
|
+
end
|
|
193
|
+
|
|
194
|
+
def indent(node)
|
|
195
|
+
' ' * node.source_range.column
|
|
196
|
+
end
|
|
197
|
+
|
|
198
|
+
def element_source(expr_node)
|
|
199
|
+
if command_call?(expr_node) || expr_node.assignment? || expr_node.rescue_type?
|
|
200
|
+
return "(#{expr_node.source})"
|
|
201
|
+
end
|
|
202
|
+
return "[#{expr_node.source}]" if expr_node.array_type? && !expr_node.bracketed?
|
|
203
|
+
|
|
204
|
+
expr_node.source
|
|
205
|
+
end
|
|
206
|
+
|
|
207
|
+
def command_call?(node)
|
|
208
|
+
node = node.send_node if node.any_block_type?
|
|
209
|
+
return false unless node.type?(:call, :super, :yield)
|
|
210
|
+
|
|
211
|
+
node.arguments? && !node.parenthesized? && !node.operator_method? && !node.setter_method?
|
|
212
|
+
end
|
|
213
|
+
end
|
|
214
|
+
end
|
|
215
|
+
end
|
|
216
|
+
end
|
|
@@ -37,6 +37,7 @@ module RuboCop
|
|
|
37
37
|
# array.sum(0)
|
|
38
38
|
# exit(true)
|
|
39
39
|
# exit!(false)
|
|
40
|
+
# string.to_i(10)
|
|
40
41
|
# string.split(" ")
|
|
41
42
|
# "first\nsecond".split(" ")
|
|
42
43
|
# string.chomp("\n")
|
|
@@ -49,6 +50,7 @@ module RuboCop
|
|
|
49
50
|
# array.sum
|
|
50
51
|
# exit
|
|
51
52
|
# exit!
|
|
53
|
+
# string.to_i
|
|
52
54
|
# string.split
|
|
53
55
|
# "first second".split
|
|
54
56
|
# string.chomp
|
|
@@ -3,8 +3,8 @@
|
|
|
3
3
|
module RuboCop
|
|
4
4
|
module Cop
|
|
5
5
|
module Style
|
|
6
|
-
# Checks for the instantiation of array using redundant `Array` constructor.
|
|
7
|
-
# Autocorrect replaces
|
|
6
|
+
# Checks for the instantiation of an array using a redundant `Array` constructor.
|
|
7
|
+
# Autocorrect replaces it with an array literal which is the simplest and fastest.
|
|
8
8
|
#
|
|
9
9
|
# @example
|
|
10
10
|
#
|
|
@@ -5,6 +5,9 @@ module RuboCop
|
|
|
5
5
|
module Style
|
|
6
6
|
# Checks for redundant assignment before returning.
|
|
7
7
|
#
|
|
8
|
+
# When there are comments between the assignment and reference,
|
|
9
|
+
# the cop will report an offense but it will not autocorrect.
|
|
10
|
+
#
|
|
8
11
|
# @example
|
|
9
12
|
# # bad
|
|
10
13
|
# def test
|
|
@@ -54,7 +57,7 @@ module RuboCop
|
|
|
54
57
|
|
|
55
58
|
private
|
|
56
59
|
|
|
57
|
-
# rubocop:disable Metrics/CyclomaticComplexity
|
|
60
|
+
# rubocop:disable-next Metrics/CyclomaticComplexity
|
|
58
61
|
def check_branch(node)
|
|
59
62
|
return unless node
|
|
60
63
|
|
|
@@ -69,7 +72,6 @@ module RuboCop
|
|
|
69
72
|
check_begin_node(node)
|
|
70
73
|
end
|
|
71
74
|
end
|
|
72
|
-
# rubocop:enable Metrics/CyclomaticComplexity
|
|
73
75
|
|
|
74
76
|
def check_case_node(node)
|
|
75
77
|
node.when_branches.each { |when_node| check_branch(when_node.body) }
|
|
@@ -99,6 +101,8 @@ module RuboCop
|
|
|
99
101
|
def check_begin_node(node)
|
|
100
102
|
if (assignment = redundant_assignment?(node))
|
|
101
103
|
add_offense(assignment) do |corrector|
|
|
104
|
+
next if comments_between_assignment_and_reference?(assignment)
|
|
105
|
+
|
|
102
106
|
expression = assignment.children[1]
|
|
103
107
|
corrector.replace(assignment, expression.source)
|
|
104
108
|
corrector.remove(assignment.right_sibling)
|
|
@@ -108,6 +112,12 @@ module RuboCop
|
|
|
108
112
|
check_branch(last_expr)
|
|
109
113
|
end
|
|
110
114
|
end
|
|
115
|
+
|
|
116
|
+
def comments_between_assignment_and_reference?(assignment)
|
|
117
|
+
line_span = assignment.source_range.line..assignment.right_sibling.source_range.line
|
|
118
|
+
|
|
119
|
+
processed_source.each_comment_in_lines(line_span).any?
|
|
120
|
+
end
|
|
111
121
|
end
|
|
112
122
|
end
|
|
113
123
|
end
|
|
@@ -3,9 +3,9 @@
|
|
|
3
3
|
module RuboCop
|
|
4
4
|
module Cop
|
|
5
5
|
module Style
|
|
6
|
-
# Checks for redundant `begin` blocks.
|
|
7
|
-
#
|
|
8
|
-
#
|
|
6
|
+
# Checks for redundant `begin` blocks. A `begin` block is redundant
|
|
7
|
+
# when the `rescue`/`ensure` can be handled by the enclosing method
|
|
8
|
+
# or block definition directly, avoiding unnecessary indentation.
|
|
9
9
|
#
|
|
10
10
|
# @example
|
|
11
11
|
#
|
|
@@ -139,7 +139,7 @@ module RuboCop
|
|
|
139
139
|
offense_range = node.loc.begin
|
|
140
140
|
|
|
141
141
|
add_offense(offense_range) do |corrector|
|
|
142
|
-
if node.parent&.assignment?
|
|
142
|
+
if node.parent&.assignment? || node.parent&.type?(:return, :next, :break)
|
|
143
143
|
replace_begin_with_statement(corrector, offense_range, node)
|
|
144
144
|
else
|
|
145
145
|
remove_begin(corrector, offense_range, node)
|
|
@@ -156,7 +156,7 @@ module RuboCop
|
|
|
156
156
|
first_child = node.children.first
|
|
157
157
|
|
|
158
158
|
source = first_child.source
|
|
159
|
-
source = "(#{source})" if
|
|
159
|
+
source = "(#{source})" if low_precedence_statement?(first_child)
|
|
160
160
|
|
|
161
161
|
corrector.replace(offense_range, source)
|
|
162
162
|
corrector.remove(range_between(offense_range.end_pos, first_child.source_range.end_pos))
|
|
@@ -164,6 +164,13 @@ module RuboCop
|
|
|
164
164
|
restore_removed_comments(corrector, offense_range, node, first_child)
|
|
165
165
|
end
|
|
166
166
|
|
|
167
|
+
def low_precedence_statement?(node)
|
|
168
|
+
return node.modifier_form? if node.basic_conditional?
|
|
169
|
+
return node.prefix_not? if node.send_type?
|
|
170
|
+
|
|
171
|
+
node.operator_keyword? && node.semantic_operator?
|
|
172
|
+
end
|
|
173
|
+
|
|
167
174
|
def remove_begin(corrector, offense_range, node)
|
|
168
175
|
if node.parent.respond_to?(:endless?) && node.parent.endless?
|
|
169
176
|
offense_range = range_with_surrounding_space(offense_range, newlines: true)
|
|
@@ -184,7 +191,8 @@ module RuboCop
|
|
|
184
191
|
def use_modifier_form_after_multiline_begin_block?(node)
|
|
185
192
|
return false unless (parent = node.parent)
|
|
186
193
|
|
|
187
|
-
node.multiline? && parent.if_type? && parent.modifier_form?
|
|
194
|
+
node.multiline? && parent.if_type? && parent.modifier_form? &&
|
|
195
|
+
!parent.condition.equal?(node)
|
|
188
196
|
end
|
|
189
197
|
|
|
190
198
|
def correct_modifier_form_after_multiline_begin_block(corrector, node)
|
|
@@ -222,7 +230,17 @@ module RuboCop
|
|
|
222
230
|
end
|
|
223
231
|
|
|
224
232
|
def valid_begin_assignment?(node)
|
|
225
|
-
node.parent&.assignment? && !node.children.one?
|
|
233
|
+
node.parent&.assignment? && (!node.children.one? || too_long_when_joined?(node))
|
|
234
|
+
end
|
|
235
|
+
|
|
236
|
+
def too_long_when_joined?(node)
|
|
237
|
+
statement = node.children.first
|
|
238
|
+
max = config.for_enabled_cop('Layout/LineLength')['Max']
|
|
239
|
+
return false unless max && statement.single_line?
|
|
240
|
+
|
|
241
|
+
length = statement.source.length
|
|
242
|
+
length += 2 if low_precedence_statement?(statement)
|
|
243
|
+
node.loc.column + length > max
|
|
226
244
|
end
|
|
227
245
|
|
|
228
246
|
def inspect_branches(node)
|
|
@@ -58,7 +58,10 @@ module RuboCop
|
|
|
58
58
|
# # good
|
|
59
59
|
# a.nil? || a
|
|
60
60
|
#
|
|
61
|
-
# @example AllowedMethods: ['nonzero?'] (default)
|
|
61
|
+
# @example AllowedMethods: ['infinite?', 'nonzero?'] (default)
|
|
62
|
+
# # good
|
|
63
|
+
# num.infinite? ? true : false
|
|
64
|
+
#
|
|
62
65
|
# # good
|
|
63
66
|
# num.nonzero? ? true : false
|
|
64
67
|
#
|
|
@@ -75,7 +78,10 @@ module RuboCop
|
|
|
75
78
|
].freeze
|
|
76
79
|
|
|
77
80
|
def on_if(node)
|
|
78
|
-
return
|
|
81
|
+
return unless redundant_condition_offense?(node)
|
|
82
|
+
return if node.each_ancestor(:if).any? do |ancestor|
|
|
83
|
+
redundant_condition_offense?(ancestor)
|
|
84
|
+
end
|
|
79
85
|
|
|
80
86
|
message = message(node)
|
|
81
87
|
|
|
@@ -86,6 +92,10 @@ module RuboCop
|
|
|
86
92
|
|
|
87
93
|
private
|
|
88
94
|
|
|
95
|
+
def redundant_condition_offense?(node)
|
|
96
|
+
!node.modifier_form? && !node.elsif_conditional? && offense?(node)
|
|
97
|
+
end
|
|
98
|
+
|
|
89
99
|
def message(node)
|
|
90
100
|
if redundant_condition?(node)
|
|
91
101
|
REDUNDANT_CONDITION
|
|
@@ -116,7 +126,7 @@ module RuboCop
|
|
|
116
126
|
end
|
|
117
127
|
|
|
118
128
|
def offense?(node)
|
|
119
|
-
_condition, _if_branch, else_branch = *node # rubocop:disable InternalAffairs/NodeDestructuring
|
|
129
|
+
_condition, _if_branch, else_branch = *node # rubocop:disable InternalAffairs/NodeDestructuring -- takes all three branches in one step
|
|
120
130
|
return false if use_if_branch?(else_branch) || use_hash_key_assignment?(else_branch)
|
|
121
131
|
|
|
122
132
|
synonymous_condition_and_branch?(node) && !node.elsif? &&
|
|
@@ -140,7 +150,7 @@ module RuboCop
|
|
|
140
150
|
end
|
|
141
151
|
|
|
142
152
|
def synonymous_condition_and_branch?(node)
|
|
143
|
-
condition, if_branch, _else_branch = *node # rubocop:disable InternalAffairs/NodeDestructuring
|
|
153
|
+
condition, if_branch, _else_branch = *node # rubocop:disable InternalAffairs/NodeDestructuring -- takes all three branches in one step
|
|
144
154
|
# e.g.
|
|
145
155
|
# if var
|
|
146
156
|
# var
|
|
@@ -177,7 +187,7 @@ module RuboCop
|
|
|
177
187
|
!use_hash_key_access?(if_branch)
|
|
178
188
|
end
|
|
179
189
|
|
|
180
|
-
# rubocop:disable Metrics/CyclomaticComplexity, Metrics/PerceivedComplexity
|
|
190
|
+
# rubocop:disable-next Metrics/CyclomaticComplexity, Metrics/PerceivedComplexity
|
|
181
191
|
def if_branch_is_true_type_and_else_is_not?(node)
|
|
182
192
|
return false unless node.ternary? || node.if?
|
|
183
193
|
|
|
@@ -187,10 +197,9 @@ module RuboCop
|
|
|
187
197
|
|
|
188
198
|
node.if_branch&.true_type? && node.else_branch && !node.else_branch.true_type?
|
|
189
199
|
end
|
|
190
|
-
# rubocop:enable Metrics/CyclomaticComplexity, Metrics/PerceivedComplexity
|
|
191
200
|
|
|
192
201
|
def branches_have_assignment?(node)
|
|
193
|
-
_condition, if_branch, else_branch = *node # rubocop:disable InternalAffairs/NodeDestructuring
|
|
202
|
+
_condition, if_branch, else_branch = *node # rubocop:disable InternalAffairs/NodeDestructuring -- takes all three branches in one step
|
|
194
203
|
|
|
195
204
|
return false unless if_branch && else_branch
|
|
196
205
|
|
|
@@ -200,7 +209,7 @@ module RuboCop
|
|
|
200
209
|
end
|
|
201
210
|
|
|
202
211
|
def asgn_type?(node)
|
|
203
|
-
node.type?(:lvasgn, :ivasgn, :cvasgn, :gvasgn)
|
|
212
|
+
node.type?(:lvasgn, :ivasgn, :cvasgn, :gvasgn, :casgn)
|
|
204
213
|
end
|
|
205
214
|
|
|
206
215
|
def branches_have_method?(node)
|
|
@@ -237,11 +246,11 @@ module RuboCop
|
|
|
237
246
|
"#{method.source}(#{arguments.source})"
|
|
238
247
|
end
|
|
239
248
|
|
|
240
|
-
# rubocop:disable Metrics/AbcSize
|
|
241
|
-
def if_source(if_branch,
|
|
249
|
+
# rubocop:disable-next Metrics/AbcSize
|
|
250
|
+
def if_source(if_branch, binary_operator)
|
|
242
251
|
if branches_have_method?(if_branch.parent) && if_branch.parenthesized?
|
|
243
252
|
if_branch.source.delete_suffix(')')
|
|
244
|
-
elsif
|
|
253
|
+
elsif binary_operator
|
|
245
254
|
argument_source = if_branch.first_argument.source
|
|
246
255
|
|
|
247
256
|
"#{if_branch.receiver.source} #{if_branch.method_name} (#{argument_source}"
|
|
@@ -254,10 +263,9 @@ module RuboCop
|
|
|
254
263
|
if_branch.source
|
|
255
264
|
end
|
|
256
265
|
end
|
|
257
|
-
# rubocop:enable Metrics/AbcSize
|
|
258
266
|
|
|
259
|
-
def else_source(else_branch,
|
|
260
|
-
if
|
|
267
|
+
def else_source(else_branch, binary_operator) # rubocop:disable Metrics/AbcSize
|
|
268
|
+
if binary_operator
|
|
261
269
|
"#{else_branch.first_argument.source})"
|
|
262
270
|
elsif branches_have_method?(else_branch.parent)
|
|
263
271
|
else_source_if_has_method(else_branch)
|
|
@@ -293,12 +301,12 @@ module RuboCop
|
|
|
293
301
|
end
|
|
294
302
|
|
|
295
303
|
def make_ternary_form(node)
|
|
296
|
-
_condition, if_branch, else_branch = *node # rubocop:disable InternalAffairs/NodeDestructuring
|
|
297
|
-
|
|
304
|
+
_condition, if_branch, else_branch = *node # rubocop:disable InternalAffairs/NodeDestructuring -- takes all three branches in one step
|
|
305
|
+
binary_operator = branches_have_method?(node) && binary_operator?(if_branch)
|
|
298
306
|
|
|
299
307
|
ternary_form = [
|
|
300
|
-
if_source(if_branch,
|
|
301
|
-
else_source(else_branch,
|
|
308
|
+
if_source(if_branch, binary_operator),
|
|
309
|
+
else_source(else_branch, binary_operator)
|
|
302
310
|
].join(' || ')
|
|
303
311
|
ternary_form += ')' if branches_have_method?(node) && if_branch.parenthesized?
|
|
304
312
|
|
|
@@ -319,17 +327,27 @@ module RuboCop
|
|
|
319
327
|
|
|
320
328
|
def require_parentheses?(node)
|
|
321
329
|
(node.basic_conditional? && node.modifier_form?) ||
|
|
322
|
-
node.range_type? ||
|
|
323
|
-
node.
|
|
324
|
-
|
|
330
|
+
node.range_type? || node.rescue_type? ||
|
|
331
|
+
(node.respond_to?(:semantic_operator?) && node.semantic_operator?) ||
|
|
332
|
+
low_precedence_keyword?(node)
|
|
333
|
+
end
|
|
334
|
+
|
|
335
|
+
# e.g. `not foo`, `return foo`, and `yield foo`
|
|
336
|
+
def low_precedence_keyword?(node)
|
|
337
|
+
return node.prefix_not? if node.send_type?
|
|
338
|
+
|
|
339
|
+
node.type?(:return, :next, :break, :yield, :super) &&
|
|
340
|
+
node.arguments? && !node.parenthesized?
|
|
325
341
|
end
|
|
326
342
|
|
|
327
343
|
def require_braces?(node)
|
|
328
344
|
node.hash_type? && !node.braces?
|
|
329
345
|
end
|
|
330
346
|
|
|
331
|
-
|
|
332
|
-
|
|
347
|
+
# Any binary operator binds tighter than `||`, so the fallback must be
|
|
348
|
+
# parenthesized as its argument, e.g. `stack << (foo || :new)`.
|
|
349
|
+
def binary_operator?(node)
|
|
350
|
+
node.binary_operation? && !node.dot?
|
|
333
351
|
end
|
|
334
352
|
|
|
335
353
|
def without_argument_parentheses_method?(node)
|
|
@@ -3,16 +3,21 @@
|
|
|
3
3
|
module RuboCop
|
|
4
4
|
module Cop
|
|
5
5
|
module Style
|
|
6
|
-
# Avoid redundant `::` prefix on constant.
|
|
6
|
+
# Avoid redundant `::` prefix on a constant.
|
|
7
7
|
#
|
|
8
|
-
# How Ruby searches
|
|
8
|
+
# How Ruby searches constants is a bit complicated, and it can often be difficult to
|
|
9
9
|
# understand from the code whether the `::` is intended or not. Where `Module.nesting`
|
|
10
10
|
# is empty, there is no need to prepend `::`, so it would be nice to consistently
|
|
11
11
|
# avoid such meaningless `::` prefix to avoid confusion.
|
|
12
12
|
#
|
|
13
|
-
# NOTE: This cop is disabled if `Lint/ConstantResolution` cop is enabled
|
|
14
|
-
# conflicting rules.
|
|
15
|
-
# `Lint/ConstantResolution` cop which is disabled by default.
|
|
13
|
+
# NOTE: This cop is disabled if `Lint/ConstantResolution` cop is enabled,
|
|
14
|
+
# to prevent conflicting rules. This is because it respects user configurations
|
|
15
|
+
# that want to enable `Lint/ConstantResolution` cop which is disabled by default.
|
|
16
|
+
#
|
|
17
|
+
# When `AllCops/UseProjectIndex` is enabled and the `rubydex` gem is
|
|
18
|
+
# installed, a leading `::` inside a namespace is also reported when the
|
|
19
|
+
# constant provably resolves to the same declaration with and without
|
|
20
|
+
# the base, i.e. nothing in the surrounding nesting shadows it.
|
|
16
21
|
#
|
|
17
22
|
# @example
|
|
18
23
|
# # bad
|
|
@@ -41,13 +46,14 @@ module RuboCop
|
|
|
41
46
|
# ::Const
|
|
42
47
|
# end
|
|
43
48
|
class RedundantConstantBase < Base
|
|
49
|
+
include ProjectIndexHelp
|
|
44
50
|
extend AutoCorrector
|
|
45
51
|
|
|
46
52
|
MSG = 'Remove redundant `::`.'
|
|
47
53
|
|
|
48
54
|
def on_cbase(node)
|
|
49
55
|
return if lint_constant_resolution_cop_enabled?
|
|
50
|
-
return unless bad?(node)
|
|
56
|
+
return unless bad?(node) || provably_unshadowed?(node)
|
|
51
57
|
|
|
52
58
|
add_offense(node) do |corrector|
|
|
53
59
|
corrector.remove(node)
|
|
@@ -56,6 +62,36 @@ module RuboCop
|
|
|
56
62
|
|
|
57
63
|
private
|
|
58
64
|
|
|
65
|
+
# When `AllCops/UseProjectIndex` is enabled, `::` inside a namespace is
|
|
66
|
+
# also redundant when the first constant segment resolves to the same
|
|
67
|
+
# declaration with and without the base, i.e. nothing in the
|
|
68
|
+
# surrounding nesting shadows it.
|
|
69
|
+
def provably_unshadowed?(node)
|
|
70
|
+
return false unless project_index
|
|
71
|
+
return false unless (segment = first_constant_segment(node))
|
|
72
|
+
|
|
73
|
+
nesting = module_nesting_ancestors_of(node)
|
|
74
|
+
.map { |ancestor| ancestor.identifier.const_name }.reverse
|
|
75
|
+
|
|
76
|
+
!nesting.empty? && same_resolution?(segment, nesting)
|
|
77
|
+
rescue StandardError
|
|
78
|
+
false
|
|
79
|
+
end
|
|
80
|
+
|
|
81
|
+
def same_resolution?(segment, nesting)
|
|
82
|
+
relative = project_index.resolve_constant(segment, nesting)
|
|
83
|
+
absolute = project_index.resolve_constant(segment, [])
|
|
84
|
+
|
|
85
|
+
!relative.nil? && !absolute.nil? && relative.name == absolute.name
|
|
86
|
+
end
|
|
87
|
+
|
|
88
|
+
def first_constant_segment(node)
|
|
89
|
+
parent = node.parent
|
|
90
|
+
return nil unless parent&.const_type?
|
|
91
|
+
|
|
92
|
+
parent.short_name.to_s
|
|
93
|
+
end
|
|
94
|
+
|
|
59
95
|
def lint_constant_resolution_cop_enabled?
|
|
60
96
|
lint_constant_resolution_config.fetch('Enabled', false)
|
|
61
97
|
end
|
|
@@ -26,7 +26,9 @@ module RuboCop
|
|
|
26
26
|
def on_send(node)
|
|
27
27
|
return unless (first_argument = node.first_argument)
|
|
28
28
|
return unless (index = first_argument.source.index(CURRENT_DIRECTORY_PREFIX))
|
|
29
|
-
|
|
29
|
+
|
|
30
|
+
content = leading_path_content(first_argument)
|
|
31
|
+
return unless (redundant_length = redundant_path_length(content))
|
|
30
32
|
|
|
31
33
|
begin_pos = first_argument.source_range.begin.begin_pos + index
|
|
32
34
|
end_pos = begin_pos + redundant_length
|
|
@@ -39,6 +41,16 @@ module RuboCop
|
|
|
39
41
|
|
|
40
42
|
private
|
|
41
43
|
|
|
44
|
+
# The literal text at the start of the path, which is the whole string
|
|
45
|
+
# for a plain string and the leading literal segment for an interpolated
|
|
46
|
+
# one (`nil` when it starts with interpolation).
|
|
47
|
+
def leading_path_content(node)
|
|
48
|
+
return node.str_content if node.str_type?
|
|
49
|
+
return unless node.dstr_type? && (first = node.children.first)&.str_type?
|
|
50
|
+
|
|
51
|
+
first.str_content
|
|
52
|
+
end
|
|
53
|
+
|
|
42
54
|
def redundant_path_length(path)
|
|
43
55
|
return unless (match = path&.match(REDUNDANT_CURRENT_DIRECTORY_PREFIX))
|
|
44
56
|
|
|
@@ -25,7 +25,13 @@ module RuboCop
|
|
|
25
25
|
MSG = 'Remove the redundant double splat and braces, use keyword arguments directly.'
|
|
26
26
|
MERGE_METHODS = %i[merge merge!].freeze
|
|
27
27
|
|
|
28
|
-
#
|
|
28
|
+
# `Style/TrailingCommaInHashLiteral` adds a comma to the hash literal whose braces
|
|
29
|
+
# this cop removes in the same pass, which would leave a dangling comma.
|
|
30
|
+
def self.autocorrect_incompatible_with
|
|
31
|
+
[Style::TrailingCommaInHashLiteral]
|
|
32
|
+
end
|
|
33
|
+
|
|
34
|
+
# rubocop:disable-next Metrics/CyclomaticComplexity, Metrics/PerceivedComplexity
|
|
29
35
|
def on_hash(node)
|
|
30
36
|
return if node.pairs.empty? || node.pairs.any?(&:hash_rocket?)
|
|
31
37
|
return unless (parent = node.parent)
|
|
@@ -38,7 +44,6 @@ module RuboCop
|
|
|
38
44
|
autocorrect(corrector, node, kwsplat)
|
|
39
45
|
end
|
|
40
46
|
end
|
|
41
|
-
# rubocop:enable Metrics/CyclomaticComplexity, Metrics/PerceivedComplexity
|
|
42
47
|
|
|
43
48
|
private
|
|
44
49
|
|
|
@@ -109,7 +114,7 @@ module RuboCop
|
|
|
109
114
|
|
|
110
115
|
node.arguments.map do |arg|
|
|
111
116
|
if arg.hash_type?
|
|
112
|
-
arg
|
|
117
|
+
hash_argument_source(arg)
|
|
113
118
|
else
|
|
114
119
|
"**#{arg.source}"
|
|
115
120
|
end
|
|
@@ -123,6 +128,15 @@ module RuboCop
|
|
|
123
128
|
|
|
124
129
|
mergeable?(parent)
|
|
125
130
|
end
|
|
131
|
+
|
|
132
|
+
# A braced hash literal passed to `merge` must have its braces stripped so
|
|
133
|
+
# its pairs join the surrounding keyword arguments. Keeping the braces would
|
|
134
|
+
# produce a positional hash after keyword arguments, which is invalid Ruby.
|
|
135
|
+
def hash_argument_source(hash)
|
|
136
|
+
return hash.source unless hash.braces?
|
|
137
|
+
|
|
138
|
+
hash.pairs.map(&:source).join(', ')
|
|
139
|
+
end
|
|
126
140
|
end
|
|
127
141
|
end
|
|
128
142
|
end
|