rubocop 1.31.1 → 1.51.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 +5 -5
- data/config/default.yml +342 -52
- data/config/obsoletion.yml +23 -1
- data/exe/rubocop +1 -1
- data/lib/rubocop/arguments_env.rb +17 -0
- data/lib/rubocop/arguments_file.rb +17 -0
- data/lib/rubocop/cache_config.rb +29 -0
- data/lib/rubocop/cli/command/{auto_genenerate_config.rb → auto_generate_config.rb} +9 -2
- data/lib/rubocop/cli/command/execute_runner.rb +14 -9
- data/lib/rubocop/cli/command/init_dotfile.rb +1 -1
- data/lib/rubocop/cli/command/suggest_extensions.rb +61 -16
- data/lib/rubocop/cli.rb +56 -9
- data/lib/rubocop/comment_config.rb +60 -1
- data/lib/rubocop/config.rb +48 -20
- data/lib/rubocop/config_finder.rb +68 -0
- data/lib/rubocop/config_loader.rb +46 -68
- data/lib/rubocop/config_loader_resolver.rb +11 -12
- data/lib/rubocop/config_obsoletion/changed_parameter.rb +5 -0
- data/lib/rubocop/config_obsoletion/parameter_rule.rb +4 -0
- data/lib/rubocop/config_obsoletion.rb +9 -4
- data/lib/rubocop/config_validator.rb +1 -1
- data/lib/rubocop/cop/autocorrect_logic.rb +29 -13
- data/lib/rubocop/cop/badge.rb +9 -4
- data/lib/rubocop/cop/base.rb +115 -83
- data/lib/rubocop/cop/bundler/gem_comment.rb +1 -1
- data/lib/rubocop/cop/commissioner.rb +19 -6
- data/lib/rubocop/cop/cop.rb +54 -34
- data/lib/rubocop/cop/corrector.rb +31 -11
- data/lib/rubocop/cop/correctors/alignment_corrector.rb +3 -3
- data/lib/rubocop/cop/correctors/each_to_for_corrector.rb +3 -3
- data/lib/rubocop/cop/correctors/for_to_each_corrector.rb +3 -3
- data/lib/rubocop/cop/correctors/line_break_corrector.rb +1 -1
- data/lib/rubocop/cop/correctors/multiline_literal_brace_corrector.rb +23 -7
- data/lib/rubocop/cop/correctors/ordered_gem_corrector.rb +2 -7
- data/lib/rubocop/cop/correctors/parentheses_corrector.rb +58 -0
- data/lib/rubocop/cop/correctors/percent_literal_corrector.rb +2 -2
- data/lib/rubocop/cop/gemspec/dependency_version.rb +17 -19
- data/lib/rubocop/cop/gemspec/deprecated_attribute_assignment.rb +1 -1
- data/lib/rubocop/cop/gemspec/development_dependencies.rb +107 -0
- data/lib/rubocop/cop/gemspec/require_mfa.rb +1 -1
- data/lib/rubocop/cop/generator/require_file_injector.rb +2 -2
- data/lib/rubocop/cop/generator.rb +5 -2
- data/lib/rubocop/cop/internal_affairs/cop_description.rb +8 -6
- data/lib/rubocop/cop/internal_affairs/create_empty_file.rb +37 -0
- data/lib/rubocop/cop/internal_affairs/example_heredoc_delimiter.rb +111 -0
- data/lib/rubocop/cop/internal_affairs/inherit_deprecated_cop_class.rb +1 -1
- data/lib/rubocop/cop/internal_affairs/lambda_or_proc.rb +46 -0
- data/lib/rubocop/cop/internal_affairs/location_expression.rb +37 -0
- data/lib/rubocop/cop/internal_affairs/node_matcher_directive.rb +3 -3
- data/lib/rubocop/cop/internal_affairs/node_type_predicate.rb +1 -1
- data/lib/rubocop/cop/internal_affairs/numblock_handler.rb +69 -0
- data/lib/rubocop/cop/internal_affairs/processed_source_buffer_name.rb +42 -0
- data/lib/rubocop/cop/internal_affairs/redundant_let_rubocop_config_new.rb +11 -3
- data/lib/rubocop/cop/internal_affairs/redundant_location_argument.rb +1 -1
- data/lib/rubocop/cop/internal_affairs/redundant_message_argument.rb +1 -1
- data/lib/rubocop/cop/internal_affairs/redundant_source_range.rb +66 -0
- data/lib/rubocop/cop/internal_affairs/single_line_comparison.rb +62 -0
- data/lib/rubocop/cop/internal_affairs/useless_restrict_on_send.rb +60 -0
- data/lib/rubocop/cop/internal_affairs.rb +9 -0
- data/lib/rubocop/cop/layout/array_alignment.rb +1 -1
- data/lib/rubocop/cop/layout/block_alignment.rb +16 -12
- data/lib/rubocop/cop/layout/block_end_newline.rb +31 -9
- data/lib/rubocop/cop/layout/class_structure.rb +37 -27
- data/lib/rubocop/cop/layout/closing_heredoc_indentation.rb +1 -1
- data/lib/rubocop/cop/layout/closing_parenthesis_indentation.rb +2 -6
- data/lib/rubocop/cop/layout/comment_indentation.rb +3 -1
- data/lib/rubocop/cop/layout/empty_comment.rb +3 -3
- data/lib/rubocop/cop/layout/empty_line_between_defs.rb +1 -1
- data/lib/rubocop/cop/layout/empty_lines.rb +3 -1
- data/lib/rubocop/cop/layout/empty_lines_around_access_modifier.rb +7 -2
- data/lib/rubocop/cop/layout/empty_lines_around_block_body.rb +2 -0
- data/lib/rubocop/cop/layout/end_alignment.rb +9 -1
- data/lib/rubocop/cop/layout/end_of_line.rb +4 -4
- data/lib/rubocop/cop/layout/extra_spacing.rb +15 -6
- data/lib/rubocop/cop/layout/first_argument_indentation.rb +15 -4
- data/lib/rubocop/cop/layout/first_array_element_indentation.rb +6 -5
- data/lib/rubocop/cop/layout/first_array_element_line_break.rb +35 -8
- data/lib/rubocop/cop/layout/first_hash_element_indentation.rb +5 -5
- data/lib/rubocop/cop/layout/first_hash_element_line_break.rb +36 -1
- data/lib/rubocop/cop/layout/first_method_argument_line_break.rb +57 -8
- data/lib/rubocop/cop/layout/first_method_parameter_line_break.rb +52 -19
- data/lib/rubocop/cop/layout/heredoc_argument_closing_parenthesis.rb +10 -4
- data/lib/rubocop/cop/layout/heredoc_indentation.rb +8 -11
- data/lib/rubocop/cop/layout/indentation_style.rb +7 -2
- data/lib/rubocop/cop/layout/indentation_width.rb +6 -2
- data/lib/rubocop/cop/layout/initial_indentation.rb +1 -1
- data/lib/rubocop/cop/layout/leading_comment_space.rb +1 -1
- data/lib/rubocop/cop/layout/line_continuation_leading_space.rb +80 -12
- data/lib/rubocop/cop/layout/line_continuation_spacing.rb +18 -8
- data/lib/rubocop/cop/layout/line_length.rb +8 -1
- data/lib/rubocop/cop/layout/multiline_array_line_breaks.rb +31 -1
- data/lib/rubocop/cop/layout/multiline_assignment_layout.rb +1 -1
- data/lib/rubocop/cop/layout/multiline_block_layout.rb +3 -1
- data/lib/rubocop/cop/layout/multiline_hash_key_line_breaks.rb +29 -1
- data/lib/rubocop/cop/layout/multiline_method_argument_line_breaks.rb +39 -2
- data/lib/rubocop/cop/layout/multiline_method_parameter_line_breaks.rb +77 -0
- data/lib/rubocop/cop/layout/redundant_line_break.rb +9 -10
- data/lib/rubocop/cop/layout/rescue_ensure_alignment.rb +2 -2
- data/lib/rubocop/cop/layout/space_around_block_parameters.rb +1 -1
- data/lib/rubocop/cop/layout/space_around_keyword.rb +3 -3
- data/lib/rubocop/cop/layout/space_around_operators.rb +1 -1
- data/lib/rubocop/cop/layout/space_before_block_braces.rb +2 -0
- data/lib/rubocop/cop/layout/space_before_first_arg.rb +1 -1
- data/lib/rubocop/cop/layout/space_in_lambda_literal.rb +2 -2
- data/lib/rubocop/cop/layout/space_inside_array_literal_brackets.rb +22 -20
- data/lib/rubocop/cop/layout/space_inside_array_percent_literal.rb +3 -0
- data/lib/rubocop/cop/layout/space_inside_block_braces.rb +27 -9
- data/lib/rubocop/cop/layout/space_inside_hash_literal_braces.rb +30 -3
- data/lib/rubocop/cop/layout/space_inside_parens.rb +2 -2
- data/lib/rubocop/cop/layout/space_inside_percent_literal_delimiters.rb +34 -0
- data/lib/rubocop/cop/layout/space_inside_reference_brackets.rb +10 -6
- data/lib/rubocop/cop/layout/space_inside_string_interpolation.rb +5 -4
- data/lib/rubocop/cop/layout/trailing_empty_lines.rb +1 -1
- data/lib/rubocop/cop/layout/trailing_whitespace.rb +12 -5
- data/lib/rubocop/cop/legacy/corrections_proxy.rb +1 -1
- data/lib/rubocop/cop/legacy/corrector.rb +1 -1
- data/lib/rubocop/cop/lint/ambiguous_block_association.rb +39 -8
- data/lib/rubocop/cop/lint/ambiguous_operator.rb +4 -0
- data/lib/rubocop/cop/lint/assignment_in_condition.rb +11 -1
- data/lib/rubocop/cop/lint/constant_resolution.rb +5 -1
- data/lib/rubocop/cop/lint/debugger.rb +27 -31
- data/lib/rubocop/cop/lint/deprecated_class_methods.rb +66 -110
- data/lib/rubocop/cop/lint/deprecated_constants.rb +8 -1
- data/lib/rubocop/cop/lint/deprecated_open_ssl_constant.rb +1 -1
- data/lib/rubocop/cop/lint/duplicate_branch.rb +0 -2
- data/lib/rubocop/cop/lint/duplicate_magic_comment.rb +73 -0
- data/lib/rubocop/cop/lint/duplicate_match_pattern.rb +122 -0
- data/lib/rubocop/cop/lint/duplicate_methods.rb +48 -18
- data/lib/rubocop/cop/lint/duplicate_regexp_character_class_element.rb +26 -9
- data/lib/rubocop/cop/lint/duplicate_require.rb +1 -1
- data/lib/rubocop/cop/lint/else_layout.rb +3 -7
- data/lib/rubocop/cop/lint/empty_block.rb +3 -7
- data/lib/rubocop/cop/lint/empty_class.rb +3 -1
- data/lib/rubocop/cop/lint/empty_conditional_body.rb +110 -2
- data/lib/rubocop/cop/lint/empty_interpolation.rb +1 -1
- data/lib/rubocop/cop/lint/erb_new_arguments.rb +11 -11
- data/lib/rubocop/cop/lint/format_parameter_mismatch.rb +14 -7
- data/lib/rubocop/cop/lint/heredoc_method_call_position.rb +15 -17
- data/lib/rubocop/cop/lint/implicit_string_concatenation.rb +1 -1
- data/lib/rubocop/cop/lint/incompatible_io_select_with_fiber_scheduler.rb +5 -2
- data/lib/rubocop/cop/lint/ineffective_access_modifier.rb +1 -1
- data/lib/rubocop/cop/lint/interpolation_check.rb +4 -3
- data/lib/rubocop/cop/lint/lambda_without_literal_block.rb +1 -1
- data/lib/rubocop/cop/lint/literal_in_interpolation.rb +48 -2
- data/lib/rubocop/cop/lint/missing_cop_enable_directive.rb +18 -3
- data/lib/rubocop/cop/lint/missing_super.rb +31 -2
- data/lib/rubocop/cop/lint/mixed_regexp_capture_types.rb +1 -0
- data/lib/rubocop/cop/lint/nested_method_definition.rb +53 -9
- data/lib/rubocop/cop/lint/next_without_accumulator.rb +25 -6
- data/lib/rubocop/cop/lint/non_atomic_file_operation.rb +68 -28
- data/lib/rubocop/cop/lint/non_deterministic_require_order.rb +12 -0
- data/lib/rubocop/cop/lint/number_conversion.rb +28 -6
- data/lib/rubocop/cop/lint/numbered_parameter_assignment.rb +2 -2
- data/lib/rubocop/cop/lint/or_assignment_to_constant.rb +2 -0
- data/lib/rubocop/cop/lint/ordered_magic_comments.rb +4 -5
- data/lib/rubocop/cop/lint/out_of_range_regexp_ref.rb +17 -2
- data/lib/rubocop/cop/lint/parentheses_as_grouped_expression.rb +5 -0
- data/lib/rubocop/cop/lint/percent_string_array.rb +1 -1
- data/lib/rubocop/cop/lint/percent_symbol_array.rb +1 -1
- data/lib/rubocop/cop/lint/redundant_cop_disable_directive.rb +49 -9
- data/lib/rubocop/cop/lint/redundant_cop_enable_directive.rb +6 -6
- data/lib/rubocop/cop/lint/redundant_dir_glob_sort.rb +7 -0
- data/lib/rubocop/cop/lint/redundant_require_statement.rb +48 -10
- data/lib/rubocop/cop/lint/redundant_safe_navigation.rb +13 -0
- data/lib/rubocop/cop/lint/redundant_splat_expansion.rb +1 -1
- data/lib/rubocop/cop/lint/redundant_string_coercion.rb +35 -15
- data/lib/rubocop/cop/lint/redundant_with_index.rb +14 -11
- data/lib/rubocop/cop/lint/redundant_with_object.rb +13 -12
- data/lib/rubocop/cop/lint/refinement_import_methods.rb +2 -1
- data/lib/rubocop/cop/lint/regexp_as_condition.rb +6 -0
- data/lib/rubocop/cop/lint/require_parentheses.rb +3 -1
- data/lib/rubocop/cop/lint/require_range_parentheses.rb +57 -0
- data/lib/rubocop/cop/lint/rescue_type.rb +3 -3
- data/lib/rubocop/cop/lint/safe_navigation_chain.rb +41 -8
- data/lib/rubocop/cop/lint/safe_navigation_consistency.rb +1 -1
- data/lib/rubocop/cop/lint/script_permission.rb +1 -1
- data/lib/rubocop/cop/lint/send_with_mixin_argument.rb +5 -4
- data/lib/rubocop/cop/lint/shadowed_exception.rb +16 -11
- data/lib/rubocop/cop/lint/shadowing_outer_local_variable.rb +28 -3
- data/lib/rubocop/cop/lint/suppressed_exception.rb +1 -1
- data/lib/rubocop/cop/lint/syntax.rb +4 -0
- data/lib/rubocop/cop/lint/to_enum_arguments.rb +13 -3
- data/lib/rubocop/cop/lint/top_level_return_with_argument.rb +23 -9
- data/lib/rubocop/cop/lint/unreachable_loop.rb +12 -6
- data/lib/rubocop/cop/lint/unused_method_argument.rb +6 -1
- data/lib/rubocop/cop/lint/useless_access_modifier.rb +17 -12
- data/lib/rubocop/cop/lint/useless_assignment.rb +56 -1
- data/lib/rubocop/cop/lint/useless_method_definition.rb +12 -4
- data/lib/rubocop/cop/lint/useless_rescue.rb +89 -0
- data/lib/rubocop/cop/lint/useless_ruby2_keywords.rb +15 -5
- data/lib/rubocop/cop/lint/useless_times.rb +1 -1
- data/lib/rubocop/cop/lint/void.rb +92 -21
- data/lib/rubocop/cop/metrics/abc_size.rb +4 -2
- data/lib/rubocop/cop/metrics/block_length.rb +16 -11
- data/lib/rubocop/cop/metrics/block_nesting.rb +2 -2
- data/lib/rubocop/cop/metrics/class_length.rb +11 -5
- data/lib/rubocop/cop/metrics/collection_literal_length.rb +76 -0
- data/lib/rubocop/cop/metrics/cyclomatic_complexity.rb +1 -1
- data/lib/rubocop/cop/metrics/method_length.rb +17 -11
- data/lib/rubocop/cop/metrics/module_length.rb +10 -5
- data/lib/rubocop/cop/metrics/parameter_lists.rb +27 -0
- data/lib/rubocop/cop/metrics/perceived_complexity.rb +1 -1
- data/lib/rubocop/cop/metrics/utils/abc_size_calculator.rb +3 -6
- data/lib/rubocop/cop/metrics/utils/code_length_calculator.rb +9 -6
- data/lib/rubocop/cop/migration/department_name.rb +1 -1
- data/lib/rubocop/cop/mixin/alignment.rb +2 -2
- data/lib/rubocop/cop/mixin/allowed_identifiers.rb +2 -2
- data/lib/rubocop/cop/mixin/allowed_methods.rb +23 -2
- data/lib/rubocop/cop/mixin/allowed_pattern.rb +17 -1
- data/lib/rubocop/cop/mixin/annotation_comment.rb +14 -7
- data/lib/rubocop/cop/mixin/check_line_breakable.rb +5 -1
- data/lib/rubocop/cop/mixin/code_length.rb +1 -1
- data/lib/rubocop/cop/mixin/comments_help.rb +29 -7
- data/lib/rubocop/cop/mixin/configurable_enforced_style.rb +21 -9
- data/lib/rubocop/cop/mixin/def_node.rb +2 -7
- data/lib/rubocop/cop/mixin/documentation_comment.rb +1 -1
- data/lib/rubocop/cop/mixin/enforce_superclass.rb +2 -1
- data/lib/rubocop/cop/mixin/first_element_line_break.rb +11 -7
- data/lib/rubocop/cop/mixin/frozen_string_literal.rb +4 -0
- data/lib/rubocop/cop/mixin/hash_alignment_styles.rb +1 -1
- data/lib/rubocop/cop/mixin/hash_shorthand_syntax.rb +152 -12
- data/lib/rubocop/cop/mixin/hash_transform_method.rb +13 -9
- data/lib/rubocop/cop/mixin/line_length_help.rb +11 -2
- data/lib/rubocop/cop/mixin/method_complexity.rb +13 -16
- data/lib/rubocop/cop/mixin/min_branches_count.rb +40 -0
- data/lib/rubocop/cop/mixin/multiline_element_indentation.rb +7 -14
- data/lib/rubocop/cop/mixin/multiline_element_line_breaks.rb +5 -6
- data/lib/rubocop/cop/mixin/ordered_gem_node.rb +1 -1
- data/lib/rubocop/cop/mixin/percent_array.rb +58 -1
- data/lib/rubocop/cop/mixin/preceding_following_alignment.rb +1 -1
- data/lib/rubocop/cop/mixin/range_help.rb +22 -5
- data/lib/rubocop/cop/mixin/require_library.rb +2 -0
- data/lib/rubocop/cop/mixin/rescue_node.rb +5 -3
- data/lib/rubocop/cop/mixin/space_after_punctuation.rb +1 -1
- data/lib/rubocop/cop/mixin/statement_modifier.rb +18 -3
- data/lib/rubocop/cop/mixin/surrounding_space.rb +13 -11
- data/lib/rubocop/cop/mixin/trailing_comma.rb +2 -2
- data/lib/rubocop/cop/mixin/visibility_help.rb +40 -5
- data/lib/rubocop/cop/naming/ascii_identifiers.rb +1 -1
- data/lib/rubocop/cop/naming/block_forwarding.rb +5 -1
- data/lib/rubocop/cop/naming/block_parameter_name.rb +1 -1
- data/lib/rubocop/cop/naming/class_and_module_camel_case.rb +3 -1
- data/lib/rubocop/cop/naming/constant_name.rb +3 -3
- data/lib/rubocop/cop/naming/heredoc_delimiter_case.rb +1 -1
- data/lib/rubocop/cop/naming/inclusive_language.rb +28 -6
- data/lib/rubocop/cop/naming/memoized_instance_variable_name.rb +22 -7
- data/lib/rubocop/cop/naming/method_name.rb +3 -3
- data/lib/rubocop/cop/naming/predicate_name.rb +31 -2
- data/lib/rubocop/cop/naming/rescued_exceptions_variable_name.rb +12 -4
- data/lib/rubocop/cop/registry.rb +73 -45
- data/lib/rubocop/cop/security/compound_hash.rb +2 -1
- data/lib/rubocop/cop/style/access_modifier_declarations.rb +92 -3
- data/lib/rubocop/cop/style/accessor_grouping.rb +46 -20
- data/lib/rubocop/cop/style/alias.rb +9 -1
- data/lib/rubocop/cop/style/arguments_forwarding.rb +6 -5
- data/lib/rubocop/cop/style/array_intersect.rb +111 -0
- data/lib/rubocop/cop/style/ascii_comments.rb +1 -1
- data/lib/rubocop/cop/style/attr.rb +11 -1
- data/lib/rubocop/cop/style/bisected_attr_accessor.rb +1 -1
- data/lib/rubocop/cop/style/block_comments.rb +2 -2
- data/lib/rubocop/cop/style/block_delimiters.rb +44 -10
- data/lib/rubocop/cop/style/case_equality.rb +40 -10
- data/lib/rubocop/cop/style/case_like_if.rb +20 -3
- data/lib/rubocop/cop/style/character_literal.rb +1 -1
- data/lib/rubocop/cop/style/class_and_module_children.rb +8 -15
- data/lib/rubocop/cop/style/class_equality_comparison.rb +94 -12
- data/lib/rubocop/cop/style/class_methods_definitions.rb +2 -1
- data/lib/rubocop/cop/style/collection_compact.rb +21 -5
- data/lib/rubocop/cop/style/collection_methods.rb +2 -0
- data/lib/rubocop/cop/style/colon_method_call.rb +2 -2
- data/lib/rubocop/cop/style/combinable_loops.rb +29 -7
- data/lib/rubocop/cop/style/command_literal.rb +1 -1
- data/lib/rubocop/cop/style/comment_annotation.rb +1 -1
- data/lib/rubocop/cop/style/commented_keyword.rb +2 -2
- data/lib/rubocop/cop/style/comparable_clamp.rb +125 -0
- data/lib/rubocop/cop/style/concat_array_literals.rb +94 -0
- data/lib/rubocop/cop/style/conditional_assignment.rb +8 -14
- data/lib/rubocop/cop/style/copyright.rb +6 -3
- data/lib/rubocop/cop/style/data_inheritance.rb +75 -0
- data/lib/rubocop/cop/style/dir_empty.rb +60 -0
- data/lib/rubocop/cop/style/disable_cops_within_source_code_directive.rb +2 -2
- data/lib/rubocop/cop/style/document_dynamic_eval_definition.rb +2 -2
- data/lib/rubocop/cop/style/documentation.rb +22 -10
- data/lib/rubocop/cop/style/documentation_method.rb +10 -4
- data/lib/rubocop/cop/style/double_negation.rb +4 -2
- data/lib/rubocop/cop/style/each_for_simple_loop.rb +41 -6
- data/lib/rubocop/cop/style/each_with_object.rb +40 -9
- data/lib/rubocop/cop/style/empty_block_parameter.rb +2 -2
- data/lib/rubocop/cop/style/empty_else.rb +37 -0
- data/lib/rubocop/cop/style/empty_heredoc.rb +73 -0
- data/lib/rubocop/cop/style/empty_lambda_parameter.rb +2 -2
- data/lib/rubocop/cop/style/empty_method.rb +1 -1
- data/lib/rubocop/cop/style/endless_method.rb +1 -1
- data/lib/rubocop/cop/style/eval_with_location.rb +4 -4
- data/lib/rubocop/cop/style/exact_regexp_match.rb +62 -0
- data/lib/rubocop/cop/style/explicit_block_argument.rb +5 -1
- data/lib/rubocop/cop/style/fetch_env_var.rb +10 -177
- data/lib/rubocop/cop/style/file_empty.rb +71 -0
- data/lib/rubocop/cop/style/file_read.rb +1 -1
- data/lib/rubocop/cop/style/file_write.rb +1 -1
- data/lib/rubocop/cop/style/for.rb +2 -0
- data/lib/rubocop/cop/style/format_string_token.rb +25 -6
- data/lib/rubocop/cop/style/frozen_string_literal_comment.rb +1 -1
- data/lib/rubocop/cop/style/guard_clause.rb +127 -38
- data/lib/rubocop/cop/style/hash_as_last_array_item.rb +1 -0
- data/lib/rubocop/cop/style/hash_each_methods.rb +48 -12
- data/lib/rubocop/cop/style/hash_except.rb +27 -16
- data/lib/rubocop/cop/style/hash_like_case.rb +3 -9
- data/lib/rubocop/cop/style/hash_syntax.rb +26 -2
- data/lib/rubocop/cop/style/identical_conditional_branches.rb +15 -0
- data/lib/rubocop/cop/style/if_inside_else.rb +6 -0
- data/lib/rubocop/cop/style/if_unless_modifier.rb +112 -16
- data/lib/rubocop/cop/style/if_with_boolean_literal_branches.rb +29 -2
- data/lib/rubocop/cop/style/if_with_semicolon.rb +4 -4
- data/lib/rubocop/cop/style/infinite_loop.rb +2 -5
- data/lib/rubocop/cop/style/inverse_methods.rb +15 -11
- data/lib/rubocop/cop/style/invertible_unless_condition.rb +118 -0
- data/lib/rubocop/cop/style/line_end_concatenation.rb +4 -1
- data/lib/rubocop/cop/style/magic_comment_format.rb +307 -0
- data/lib/rubocop/cop/style/map_compact_with_conditional_block.rb +2 -2
- data/lib/rubocop/cop/style/map_to_hash.rb +4 -1
- data/lib/rubocop/cop/style/map_to_set.rb +64 -0
- data/lib/rubocop/cop/style/method_call_with_args_parentheses/omit_parentheses.rb +40 -24
- data/lib/rubocop/cop/style/method_call_with_args_parentheses/require_parentheses.rb +5 -1
- data/lib/rubocop/cop/style/method_call_with_args_parentheses.rb +48 -41
- data/lib/rubocop/cop/style/method_call_without_args_parentheses.rb +21 -2
- data/lib/rubocop/cop/style/method_called_on_do_end_block.rb +4 -1
- data/lib/rubocop/cop/style/method_def_parentheses.rb +11 -4
- data/lib/rubocop/cop/style/min_max.rb +3 -3
- data/lib/rubocop/cop/style/min_max_comparison.rb +83 -0
- data/lib/rubocop/cop/style/missing_else.rb +13 -1
- data/lib/rubocop/cop/style/mixin_grouping.rb +4 -4
- data/lib/rubocop/cop/style/module_function.rb +30 -8
- data/lib/rubocop/cop/style/multiline_block_chain.rb +3 -1
- data/lib/rubocop/cop/style/multiline_if_modifier.rb +0 -4
- data/lib/rubocop/cop/style/multiline_in_pattern_then.rb +1 -1
- data/lib/rubocop/cop/style/multiline_memoization.rb +2 -2
- data/lib/rubocop/cop/style/multiline_method_signature.rb +7 -4
- data/lib/rubocop/cop/style/multiline_ternary_operator.rb +18 -3
- data/lib/rubocop/cop/style/negated_if_else_condition.rb +17 -10
- data/lib/rubocop/cop/style/nested_parenthesized_calls.rb +9 -0
- data/lib/rubocop/cop/style/next.rb +3 -5
- data/lib/rubocop/cop/style/nil_lambda.rb +4 -4
- data/lib/rubocop/cop/style/numbered_parameters_limit.rb +11 -3
- data/lib/rubocop/cop/style/numeric_literals.rb +16 -1
- data/lib/rubocop/cop/style/numeric_predicate.rb +43 -9
- data/lib/rubocop/cop/style/object_then.rb +5 -0
- data/lib/rubocop/cop/style/one_line_conditional.rb +3 -6
- data/lib/rubocop/cop/style/operator_method_call.rb +67 -0
- data/lib/rubocop/cop/style/parallel_assignment.rb +29 -19
- data/lib/rubocop/cop/style/percent_literal_delimiters.rb +2 -3
- data/lib/rubocop/cop/style/percent_q_literals.rb +1 -1
- data/lib/rubocop/cop/style/perl_backrefs.rb +22 -1
- data/lib/rubocop/cop/style/proc.rb +4 -1
- data/lib/rubocop/cop/style/quoted_symbols.rb +1 -1
- data/lib/rubocop/cop/style/redundant_argument.rb +3 -0
- data/lib/rubocop/cop/style/redundant_begin.rb +3 -0
- data/lib/rubocop/cop/style/redundant_condition.rb +41 -8
- data/lib/rubocop/cop/style/redundant_conditional.rb +0 -4
- data/lib/rubocop/cop/style/redundant_constant_base.rb +85 -0
- data/lib/rubocop/cop/style/redundant_double_splat_hash_braces.rb +45 -0
- data/lib/rubocop/cop/style/redundant_each.rb +116 -0
- data/lib/rubocop/cop/style/redundant_fetch_block.rb +7 -5
- data/lib/rubocop/cop/style/redundant_heredoc_delimiter_quotes.rb +58 -0
- data/lib/rubocop/cop/style/redundant_initialize.rb +3 -1
- data/lib/rubocop/cop/style/redundant_interpolation.rb +2 -2
- data/lib/rubocop/cop/style/redundant_line_continuation.rb +183 -0
- data/lib/rubocop/cop/style/redundant_parentheses.rb +22 -24
- data/lib/rubocop/cop/style/redundant_percent_q.rb +1 -1
- data/lib/rubocop/cop/style/redundant_regexp_character_class.rb +9 -3
- data/lib/rubocop/cop/style/redundant_regexp_escape.rb +21 -4
- data/lib/rubocop/cop/style/redundant_return.rb +7 -0
- data/lib/rubocop/cop/style/redundant_self.rb +2 -0
- data/lib/rubocop/cop/style/redundant_sort.rb +24 -9
- data/lib/rubocop/cop/style/redundant_sort_by.rb +24 -8
- data/lib/rubocop/cop/style/redundant_string_escape.rb +183 -0
- data/lib/rubocop/cop/style/regexp_literal.rb +11 -2
- data/lib/rubocop/cop/style/require_order.rb +138 -0
- data/lib/rubocop/cop/style/rescue_modifier.rb +1 -1
- data/lib/rubocop/cop/style/rescue_standard_error.rb +2 -2
- data/lib/rubocop/cop/style/safe_navigation.rb +41 -10
- data/lib/rubocop/cop/style/select_by_regexp.rb +13 -5
- data/lib/rubocop/cop/style/self_assignment.rb +2 -2
- data/lib/rubocop/cop/style/semicolon.rb +63 -5
- data/lib/rubocop/cop/style/signal_exception.rb +8 -6
- data/lib/rubocop/cop/style/single_line_block_params.rb +1 -1
- data/lib/rubocop/cop/style/slicing_with_range.rb +1 -1
- data/lib/rubocop/cop/style/sole_nested_conditional.rb +17 -8
- data/lib/rubocop/cop/style/special_global_vars.rb +2 -2
- data/lib/rubocop/cop/style/static_class.rb +32 -1
- data/lib/rubocop/cop/style/stderr_puts.rb +1 -1
- data/lib/rubocop/cop/style/string_hash_keys.rb +4 -1
- data/lib/rubocop/cop/style/string_literals.rb +1 -5
- data/lib/rubocop/cop/style/struct_inheritance.rb +1 -1
- data/lib/rubocop/cop/style/symbol_array.rb +6 -5
- data/lib/rubocop/cop/style/symbol_proc.rb +42 -10
- data/lib/rubocop/cop/style/ternary_parentheses.rb +1 -13
- data/lib/rubocop/cop/style/top_level_method_definition.rb +3 -1
- data/lib/rubocop/cop/style/trailing_body_on_class.rb +1 -0
- data/lib/rubocop/cop/style/trailing_comma_in_arguments.rb +4 -4
- data/lib/rubocop/cop/style/trailing_comma_in_block_args.rb +1 -1
- data/lib/rubocop/cop/style/trailing_underscore_variable.rb +1 -1
- data/lib/rubocop/cop/style/trivial_accessors.rb +4 -1
- data/lib/rubocop/cop/style/unless_logical_operators.rb +1 -0
- data/lib/rubocop/cop/style/unpack_first.rb +3 -3
- data/lib/rubocop/cop/style/word_array.rb +59 -5
- data/lib/rubocop/cop/style/yoda_condition.rb +13 -6
- data/lib/rubocop/cop/style/yoda_expression.rb +90 -0
- data/lib/rubocop/cop/style/zero_length_predicate.rb +40 -19
- data/lib/rubocop/cop/team.rb +63 -56
- data/lib/rubocop/cop/util.rb +44 -8
- data/lib/rubocop/cop/variable_force/assignment.rb +5 -1
- data/lib/rubocop/cop/variable_force/scope.rb +3 -3
- data/lib/rubocop/cop/variable_force/variable.rb +5 -3
- data/lib/rubocop/cop/variable_force/variable_table.rb +6 -4
- data/lib/rubocop/cop/variable_force.rb +18 -30
- data/lib/rubocop/cops_documentation_generator.rb +45 -15
- data/lib/rubocop/directive_comment.rb +4 -4
- data/lib/rubocop/ext/comment.rb +18 -0
- data/lib/rubocop/ext/processed_source.rb +2 -0
- data/lib/rubocop/ext/range.rb +15 -0
- data/lib/rubocop/ext/regexp_node.rb +1 -1
- data/lib/rubocop/ext/regexp_parser.rb +1 -1
- data/lib/rubocop/feature_loader.rb +94 -0
- data/lib/rubocop/file_patterns.rb +43 -0
- data/lib/rubocop/formatter/clang_style_formatter.rb +1 -1
- data/lib/rubocop/formatter/disabled_config_formatter.rb +26 -9
- data/lib/rubocop/formatter/html_formatter.rb +4 -4
- data/lib/rubocop/formatter/junit_formatter.rb +4 -1
- data/lib/rubocop/formatter/markdown_formatter.rb +1 -1
- data/lib/rubocop/formatter/offense_count_formatter.rb +8 -5
- data/lib/rubocop/formatter/simple_text_formatter.rb +1 -1
- data/lib/rubocop/formatter/tap_formatter.rb +1 -1
- data/lib/rubocop/formatter/worst_offenders_formatter.rb +6 -3
- data/lib/rubocop/formatter.rb +4 -1
- data/lib/rubocop/options.rb +55 -22
- data/lib/rubocop/path_util.rb +50 -22
- data/lib/rubocop/rake_task.rb +5 -1
- data/lib/rubocop/result_cache.rb +26 -24
- data/lib/rubocop/rspec/cop_helper.rb +26 -3
- data/lib/rubocop/rspec/expect_offense.rb +6 -4
- data/lib/rubocop/rspec/shared_contexts.rb +31 -14
- data/lib/rubocop/rspec/support.rb +17 -2
- data/lib/rubocop/runner.rb +73 -18
- data/lib/rubocop/server/cache.rb +48 -2
- data/lib/rubocop/server/cli.rb +62 -19
- data/lib/rubocop/server/client_command/base.rb +1 -1
- data/lib/rubocop/server/client_command/exec.rb +6 -1
- data/lib/rubocop/server/client_command/start.rb +6 -1
- data/lib/rubocop/server/core.rb +42 -10
- data/lib/rubocop/server/helper.rb +1 -1
- data/lib/rubocop/server/server_command/exec.rb +1 -1
- data/lib/rubocop/server/socket_reader.rb +5 -1
- data/lib/rubocop/server.rb +1 -1
- data/lib/rubocop/target_finder.rb +1 -1
- data/lib/rubocop/target_ruby.rb +5 -5
- data/lib/rubocop/version.rb +10 -4
- data/lib/rubocop.rb +45 -9
- metadata +58 -33
- data/lib/rubocop/cop/mixin/ignored_methods.rb +0 -52
@@ -6,6 +6,13 @@ module RuboCop
|
|
6
6
|
# Use a guard clause instead of wrapping the code inside a conditional
|
7
7
|
# expression
|
8
8
|
#
|
9
|
+
# A condition with an `elsif` or `else` branch is allowed unless
|
10
|
+
# one of `return`, `break`, `next`, `raise`, or `fail` is used
|
11
|
+
# in the body of the conditional expression.
|
12
|
+
#
|
13
|
+
# NOTE: Autocorrect works in most cases except with if-else statements
|
14
|
+
# that contain logical operators such as `foo || raise('exception')`
|
15
|
+
#
|
9
16
|
# @example
|
10
17
|
# # bad
|
11
18
|
# def test
|
@@ -50,35 +57,44 @@ module RuboCop
|
|
50
57
|
#
|
51
58
|
# @example AllowConsecutiveConditionals: false (default)
|
52
59
|
# # bad
|
53
|
-
#
|
54
|
-
#
|
55
|
-
#
|
60
|
+
# def test
|
61
|
+
# if foo?
|
62
|
+
# work
|
63
|
+
# end
|
56
64
|
#
|
57
|
-
#
|
58
|
-
#
|
65
|
+
# if bar? # <- reports an offense
|
66
|
+
# work
|
67
|
+
# end
|
59
68
|
# end
|
60
69
|
#
|
61
70
|
# @example AllowConsecutiveConditionals: true
|
62
71
|
# # good
|
63
|
-
#
|
64
|
-
#
|
65
|
-
#
|
72
|
+
# def test
|
73
|
+
# if foo?
|
74
|
+
# work
|
75
|
+
# end
|
66
76
|
#
|
67
|
-
#
|
68
|
-
#
|
77
|
+
# if bar?
|
78
|
+
# work
|
79
|
+
# end
|
69
80
|
# end
|
70
81
|
#
|
71
82
|
# # bad
|
72
|
-
#
|
73
|
-
#
|
74
|
-
#
|
83
|
+
# def test
|
84
|
+
# if foo?
|
85
|
+
# work
|
86
|
+
# end
|
75
87
|
#
|
76
|
-
#
|
88
|
+
# do_something
|
77
89
|
#
|
78
|
-
#
|
79
|
-
#
|
90
|
+
# if bar? # <- reports an offense
|
91
|
+
# work
|
92
|
+
# end
|
80
93
|
# end
|
94
|
+
#
|
81
95
|
class GuardClause < Base
|
96
|
+
extend AutoCorrector
|
97
|
+
include RangeHelp
|
82
98
|
include MinBodyLength
|
83
99
|
include StatementModifier
|
84
100
|
|
@@ -90,40 +106,49 @@ module RuboCop
|
|
90
106
|
|
91
107
|
return unless body
|
92
108
|
|
93
|
-
|
94
|
-
check_ending_if(body)
|
95
|
-
elsif body.begin_type?
|
96
|
-
final_expression = body.children.last
|
97
|
-
check_ending_if(final_expression) if final_expression&.if_type?
|
98
|
-
end
|
109
|
+
check_ending_body(body)
|
99
110
|
end
|
100
111
|
alias on_defs on_def
|
101
112
|
|
102
113
|
def on_if(node)
|
103
114
|
return if accepted_form?(node)
|
104
115
|
|
105
|
-
|
106
|
-
|
107
|
-
|
108
|
-
|
116
|
+
if (guard_clause = node.if_branch&.guard_clause?)
|
117
|
+
kw = node.loc.keyword.source
|
118
|
+
guard = :if
|
119
|
+
elsif (guard_clause = node.else_branch&.guard_clause?)
|
120
|
+
kw = node.inverse_keyword
|
121
|
+
guard = :else
|
122
|
+
else
|
123
|
+
return
|
124
|
+
end
|
109
125
|
|
110
|
-
|
111
|
-
node.loc.keyword.source
|
112
|
-
else
|
113
|
-
node.inverse_keyword
|
114
|
-
end
|
126
|
+
guard = nil if and_or_guard_clause?(guard_clause)
|
115
127
|
|
116
|
-
register_offense(node, guard_clause_source(guard_clause), kw)
|
128
|
+
register_offense(node, guard_clause_source(guard_clause), kw, guard)
|
117
129
|
end
|
118
130
|
|
119
131
|
private
|
120
132
|
|
133
|
+
def check_ending_body(body)
|
134
|
+
return if body.nil?
|
135
|
+
|
136
|
+
if body.if_type?
|
137
|
+
check_ending_if(body)
|
138
|
+
elsif body.begin_type?
|
139
|
+
final_expression = body.children.last
|
140
|
+
check_ending_if(final_expression) if final_expression&.if_type?
|
141
|
+
end
|
142
|
+
end
|
143
|
+
|
121
144
|
def check_ending_if(node)
|
122
145
|
return if accepted_form?(node, ending: true) || !min_body_length?(node)
|
123
146
|
return if allowed_consecutive_conditionals? &&
|
124
147
|
consecutive_conditionals?(node.parent, node)
|
125
148
|
|
126
149
|
register_offense(node, 'return', node.inverse_keyword)
|
150
|
+
|
151
|
+
check_ending_body(node.if_branch)
|
127
152
|
end
|
128
153
|
|
129
154
|
def consecutive_conditionals?(parent, node)
|
@@ -134,28 +159,88 @@ module RuboCop
|
|
134
159
|
end
|
135
160
|
end
|
136
161
|
|
137
|
-
def register_offense(node, scope_exiting_keyword, conditional_keyword)
|
162
|
+
def register_offense(node, scope_exiting_keyword, conditional_keyword, guard = nil)
|
138
163
|
condition, = node.node_parts
|
139
164
|
example = [scope_exiting_keyword, conditional_keyword, condition.source].join(' ')
|
140
165
|
if too_long_for_single_line?(node, example)
|
141
166
|
return if trivial?(node)
|
142
167
|
|
143
168
|
example = "#{conditional_keyword} #{condition.source}; #{scope_exiting_keyword}; end"
|
169
|
+
replacement = <<~RUBY.chomp
|
170
|
+
#{conditional_keyword} #{condition.source}
|
171
|
+
#{scope_exiting_keyword}
|
172
|
+
end
|
173
|
+
RUBY
|
144
174
|
end
|
145
175
|
|
146
|
-
add_offense(node.loc.keyword, message: format(MSG, example: example))
|
176
|
+
add_offense(node.loc.keyword, message: format(MSG, example: example)) do |corrector|
|
177
|
+
next if node.else? && guard.nil?
|
178
|
+
|
179
|
+
autocorrect(corrector, node, condition, replacement || example, guard)
|
180
|
+
end
|
147
181
|
end
|
148
182
|
|
149
|
-
|
150
|
-
|
183
|
+
# rubocop:disable Metrics/AbcSize, Metrics/CyclomaticComplexity, Metrics/PerceivedComplexity
|
184
|
+
def autocorrect(corrector, node, condition, replacement, guard)
|
185
|
+
corrector.replace(node.loc.keyword.join(condition.source_range), replacement)
|
186
|
+
|
187
|
+
if_branch = node.if_branch
|
188
|
+
else_branch = node.else_branch
|
189
|
+
|
190
|
+
corrector.replace(node.loc.begin, "\n") if node.loc.begin&.is?('then')
|
191
|
+
|
192
|
+
if if_branch&.send_type? && heredoc?(if_branch.last_argument)
|
193
|
+
autocorrect_heredoc_argument(corrector, node, if_branch, else_branch, guard)
|
194
|
+
elsif else_branch&.send_type? && heredoc?(else_branch.last_argument)
|
195
|
+
autocorrect_heredoc_argument(corrector, node, else_branch, if_branch, guard)
|
196
|
+
else
|
197
|
+
corrector.remove(node.loc.end)
|
198
|
+
return unless node.else?
|
151
199
|
|
152
|
-
|
200
|
+
corrector.remove(node.loc.else)
|
201
|
+
corrector.remove(range_of_branch_to_remove(node, guard))
|
202
|
+
end
|
203
|
+
end
|
204
|
+
# rubocop:enable Metrics/AbcSize, Metrics/CyclomaticComplexity, Metrics/PerceivedComplexity
|
205
|
+
|
206
|
+
def heredoc?(argument)
|
207
|
+
argument.respond_to?(:heredoc?) && argument.heredoc?
|
208
|
+
end
|
209
|
+
|
210
|
+
def autocorrect_heredoc_argument(corrector, node, heredoc_branch, leave_branch, guard)
|
211
|
+
return unless node.else?
|
212
|
+
|
213
|
+
remove_whole_lines(corrector, leave_branch.source_range)
|
214
|
+
remove_whole_lines(corrector, node.loc.else)
|
215
|
+
remove_whole_lines(corrector, node.loc.end)
|
216
|
+
remove_whole_lines(corrector, range_of_branch_to_remove(node, guard))
|
217
|
+
corrector.insert_after(
|
218
|
+
heredoc_branch.last_argument.loc.heredoc_end, "\n#{leave_branch.source}"
|
219
|
+
)
|
220
|
+
end
|
221
|
+
|
222
|
+
def range_of_branch_to_remove(node, guard)
|
223
|
+
branch = case guard
|
224
|
+
when :if then node.if_branch
|
225
|
+
when :else then node.else_branch
|
226
|
+
end
|
227
|
+
|
228
|
+
branch.source_range
|
229
|
+
end
|
230
|
+
|
231
|
+
def guard_clause_source(guard_clause)
|
232
|
+
if and_or_guard_clause?(guard_clause)
|
153
233
|
guard_clause.parent.source
|
154
234
|
else
|
155
235
|
guard_clause.source
|
156
236
|
end
|
157
237
|
end
|
158
238
|
|
239
|
+
def and_or_guard_clause?(guard_clause)
|
240
|
+
parent = guard_clause.parent
|
241
|
+
parent.and_type? || parent.or_type?
|
242
|
+
end
|
243
|
+
|
159
244
|
def too_long_for_single_line?(node, example)
|
160
245
|
max = max_line_length
|
161
246
|
max && node.source_range.column + example.length > max
|
@@ -170,7 +255,7 @@ module RuboCop
|
|
170
255
|
end
|
171
256
|
|
172
257
|
def accepted_if?(node, ending)
|
173
|
-
return true if node.modifier_form? || node.ternary?
|
258
|
+
return true if node.modifier_form? || node.ternary? || node.elsif_conditional?
|
174
259
|
|
175
260
|
if ending
|
176
261
|
node.else?
|
@@ -179,6 +264,10 @@ module RuboCop
|
|
179
264
|
end
|
180
265
|
end
|
181
266
|
|
267
|
+
def remove_whole_lines(corrector, range)
|
268
|
+
corrector.remove(range_by_whole_lines(range, include_final_newline: true))
|
269
|
+
end
|
270
|
+
|
182
271
|
def allowed_consecutive_conditionals?
|
183
272
|
cop_config.fetch('AllowConsecutiveConditionals', false)
|
184
273
|
end
|
@@ -35,29 +35,53 @@ module RuboCop
|
|
35
35
|
|
36
36
|
# @!method kv_each(node)
|
37
37
|
def_node_matcher :kv_each, <<~PATTERN
|
38
|
-
(block $(send (send _ ${:keys :values}) :each) ...)
|
38
|
+
({block numblock} $(send (send _ ${:keys :values}) :each) ...)
|
39
|
+
PATTERN
|
40
|
+
|
41
|
+
# @!method kv_each_with_block_pass(node)
|
42
|
+
def_node_matcher :kv_each_with_block_pass, <<~PATTERN
|
43
|
+
(send $(send _ ${:keys :values}) :each (block_pass (sym _)))
|
39
44
|
PATTERN
|
40
45
|
|
41
46
|
def on_block(node)
|
42
|
-
|
47
|
+
kv_each(node) do |target, method|
|
48
|
+
register_kv_offense(target, method)
|
49
|
+
end
|
50
|
+
end
|
51
|
+
|
52
|
+
alias on_numblock on_block
|
53
|
+
|
54
|
+
def on_block_pass(node)
|
55
|
+
kv_each_with_block_pass(node.parent) do |target, method|
|
56
|
+
register_kv_with_block_pass_offense(node, target, method)
|
57
|
+
end
|
43
58
|
end
|
44
59
|
|
45
60
|
private
|
46
61
|
|
47
|
-
def register_kv_offense(
|
48
|
-
|
49
|
-
|
50
|
-
return unless parent_receiver
|
51
|
-
return if allowed_receiver?(parent_receiver)
|
62
|
+
def register_kv_offense(target, method)
|
63
|
+
return unless (parent_receiver = target.receiver.receiver)
|
64
|
+
return if allowed_receiver?(parent_receiver)
|
52
65
|
|
53
|
-
|
66
|
+
add_offense(kv_range(target), message: format_message(method)) do |corrector|
|
67
|
+
correct_key_value_each(target, corrector)
|
68
|
+
end
|
69
|
+
end
|
54
70
|
|
55
|
-
|
56
|
-
|
57
|
-
|
71
|
+
def register_kv_with_block_pass_offense(node, target, method)
|
72
|
+
return unless (parent_receiver = node.parent.receiver.receiver)
|
73
|
+
return if allowed_receiver?(parent_receiver)
|
74
|
+
|
75
|
+
range = target.loc.selector.with(end_pos: node.parent.loc.selector.end_pos)
|
76
|
+
add_offense(range, message: format_message(method)) do |corrector|
|
77
|
+
corrector.replace(range, "each_#{method[0..-2]}")
|
58
78
|
end
|
59
79
|
end
|
60
80
|
|
81
|
+
def format_message(method_name)
|
82
|
+
format(MSG, prefer: "each_#{method_name[0..-2]}", current: "#{method_name}.each")
|
83
|
+
end
|
84
|
+
|
61
85
|
def check_argument(variable)
|
62
86
|
return unless variable.block_argument?
|
63
87
|
|
@@ -94,11 +118,23 @@ module RuboCop
|
|
94
118
|
end
|
95
119
|
|
96
120
|
def allowed_receiver?(receiver)
|
97
|
-
receiver_name = receiver
|
121
|
+
receiver_name = receiver_name(receiver)
|
98
122
|
|
99
123
|
allowed_receivers.include?(receiver_name)
|
100
124
|
end
|
101
125
|
|
126
|
+
def receiver_name(receiver)
|
127
|
+
if receiver.send_type?
|
128
|
+
if receiver.receiver
|
129
|
+
"#{receiver_name(receiver.receiver)}.#{receiver.method_name}"
|
130
|
+
else
|
131
|
+
receiver.method_name.to_s
|
132
|
+
end
|
133
|
+
else
|
134
|
+
receiver.source
|
135
|
+
end
|
136
|
+
end
|
137
|
+
|
102
138
|
def allowed_receivers
|
103
139
|
cop_config.fetch('AllowedReceivers', [])
|
104
140
|
end
|
@@ -13,6 +13,10 @@ module RuboCop
|
|
13
13
|
# when used `==`.
|
14
14
|
# And do not check `Hash#delete_if` and `Hash#keep_if` to change receiver object.
|
15
15
|
#
|
16
|
+
# @safety
|
17
|
+
# This cop is unsafe because it cannot be guaranteed that the receiver
|
18
|
+
# is a `Hash` or responds to the replacement method.
|
19
|
+
#
|
16
20
|
# @example
|
17
21
|
#
|
18
22
|
# # bad
|
@@ -41,13 +45,13 @@ module RuboCop
|
|
41
45
|
(block
|
42
46
|
(send _ _)
|
43
47
|
(args
|
44
|
-
(arg _)
|
48
|
+
$(arg _)
|
45
49
|
(arg _))
|
46
50
|
{
|
47
|
-
(send
|
51
|
+
$(send
|
48
52
|
_ {:== :!= :eql? :include?} _)
|
49
53
|
(send
|
50
|
-
(send
|
54
|
+
$(send
|
51
55
|
_ {:== :!= :eql? :include?} _) :!)
|
52
56
|
})
|
53
57
|
PATTERN
|
@@ -57,13 +61,13 @@ module RuboCop
|
|
57
61
|
(block
|
58
62
|
(send _ _)
|
59
63
|
(args
|
60
|
-
(arg _)
|
64
|
+
$(arg _)
|
61
65
|
(arg _))
|
62
66
|
{
|
63
|
-
(send
|
67
|
+
$(send
|
64
68
|
_ {:== :!= :eql? :in? :include? :exclude?} _)
|
65
69
|
(send
|
66
|
-
(send
|
70
|
+
$(send
|
67
71
|
_ {:== :!= :eql? :in? :include? :exclude?} _) :!)
|
68
72
|
})
|
69
73
|
PATTERN
|
@@ -85,13 +89,24 @@ module RuboCop
|
|
85
89
|
|
86
90
|
private
|
87
91
|
|
92
|
+
# rubocop:disable Metrics/AbcSize, Metrics/CyclomaticComplexity, Metrics/PerceivedComplexity
|
88
93
|
def bad_method?(block)
|
89
94
|
if active_support_extensions_enabled?
|
90
|
-
bad_method_with_active_support?(block)
|
95
|
+
bad_method_with_active_support?(block) do |key_arg, send_node|
|
96
|
+
if send_node.method?(:in?) && send_node.receiver&.source != key_arg.source
|
97
|
+
return false
|
98
|
+
end
|
99
|
+
return true if !send_node.method?(:include?) && !send_node.method?(:exclude?)
|
100
|
+
|
101
|
+
send_node.first_argument&.source == key_arg.source
|
102
|
+
end
|
91
103
|
else
|
92
|
-
bad_method_with_poro?(block)
|
104
|
+
bad_method_with_poro?(block) do |key_arg, send_node|
|
105
|
+
!send_node.method?(:include?) || send_node.first_argument&.source == key_arg.source
|
106
|
+
end
|
93
107
|
end
|
94
108
|
end
|
109
|
+
# rubocop:enable Metrics/AbcSize, Metrics/CyclomaticComplexity, Metrics/PerceivedComplexity
|
95
110
|
|
96
111
|
def semantically_except_method?(send, block)
|
97
112
|
body = block.body
|
@@ -118,8 +133,8 @@ module RuboCop
|
|
118
133
|
end
|
119
134
|
|
120
135
|
def safe_to_register_offense?(block, except_key)
|
121
|
-
extracted =
|
122
|
-
if extracted.method?('in?') || extracted.method?('include?') ||
|
136
|
+
extracted = extract_body_if_negated(block.body)
|
137
|
+
if extracted.method?('in?') || extracted.method?('include?') ||
|
123
138
|
extracted.method?('exclude?')
|
124
139
|
return true
|
125
140
|
end
|
@@ -128,7 +143,7 @@ module RuboCop
|
|
128
143
|
except_key.sym_type? || except_key.str_type?
|
129
144
|
end
|
130
145
|
|
131
|
-
def
|
146
|
+
def extract_body_if_negated(body)
|
132
147
|
return body unless body.method?('!')
|
133
148
|
|
134
149
|
body.receiver
|
@@ -157,12 +172,8 @@ module RuboCop
|
|
157
172
|
|
158
173
|
def except_key(node)
|
159
174
|
key_argument = node.argument_list.first.source
|
160
|
-
body =
|
175
|
+
body = extract_body_if_negated(node.body)
|
161
176
|
lhs, _method_name, rhs = *body
|
162
|
-
|
163
|
-
return lhs if body.method?('include?')
|
164
|
-
return lhs if body.method?('exclude?')
|
165
|
-
return rhs if body.method?('in?')
|
166
177
|
return if [lhs, rhs].map(&:source).none?(key_argument)
|
167
178
|
|
168
179
|
[lhs, rhs].find { |operand| operand.source != key_argument }
|
@@ -37,6 +37,8 @@ module RuboCop
|
|
37
37
|
# end
|
38
38
|
#
|
39
39
|
class HashLikeCase < Base
|
40
|
+
include MinBranchesCount
|
41
|
+
|
40
42
|
MSG = 'Consider replacing `case-when` with a hash lookup.'
|
41
43
|
|
42
44
|
# @!method hash_like_case?(node)
|
@@ -49,7 +51,7 @@ module RuboCop
|
|
49
51
|
PATTERN
|
50
52
|
|
51
53
|
def on_case(node)
|
52
|
-
return
|
54
|
+
return unless min_branches_count?(node)
|
53
55
|
|
54
56
|
hash_like_case?(node) do |condition_nodes, body_nodes|
|
55
57
|
if nodes_of_same_type?(condition_nodes) && nodes_of_same_type?(body_nodes)
|
@@ -63,14 +65,6 @@ module RuboCop
|
|
63
65
|
def nodes_of_same_type?(nodes)
|
64
66
|
nodes.all? { |node| node.type == nodes.first.type }
|
65
67
|
end
|
66
|
-
|
67
|
-
def min_branches_count
|
68
|
-
length = cop_config['MinBranchesCount'] || 3
|
69
|
-
return length if length.is_a?(Integer) && length.positive?
|
70
|
-
|
71
|
-
warn Rainbow('`MinBranchesCount` needs to be a positive integer!').red
|
72
|
-
exit!
|
73
|
-
end
|
74
68
|
end
|
75
69
|
end
|
76
70
|
end
|
@@ -28,6 +28,7 @@ module RuboCop
|
|
28
28
|
# * always - forces use of the 3.1 syntax (e.g. {foo:})
|
29
29
|
# * never - forces use of explicit hash literal value
|
30
30
|
# * either - accepts both shorthand and explicit use of hash literal value
|
31
|
+
# * consistent - forces use of the 3.1 syntax only if all values can be omitted in the hash
|
31
32
|
#
|
32
33
|
# @example EnforcedStyle: ruby19 (default)
|
33
34
|
# # bad
|
@@ -87,8 +88,28 @@ module RuboCop
|
|
87
88
|
# {foo: foo, bar: bar}
|
88
89
|
#
|
89
90
|
# # good
|
91
|
+
# {foo: foo, bar:}
|
92
|
+
#
|
93
|
+
# # good
|
94
|
+
# {foo:, bar:}
|
95
|
+
#
|
96
|
+
# @example EnforcedShorthandSyntax: consistent
|
97
|
+
#
|
98
|
+
# # bad - `foo` and `bar` values can be omitted
|
99
|
+
# {foo: foo, bar: bar}
|
100
|
+
#
|
101
|
+
# # bad - `bar` value can be omitted
|
102
|
+
# {foo:, bar: bar}
|
103
|
+
#
|
104
|
+
# # bad - mixed syntaxes
|
105
|
+
# {foo:, bar: baz}
|
106
|
+
#
|
107
|
+
# # good
|
90
108
|
# {foo:, bar:}
|
91
109
|
#
|
110
|
+
# # good - can't omit `baz`
|
111
|
+
# {foo: foo, bar: baz}
|
112
|
+
#
|
92
113
|
class HashSyntax < Base
|
93
114
|
include ConfigurableEnforcedStyle
|
94
115
|
include HashShorthandSyntax
|
@@ -104,6 +125,8 @@ module RuboCop
|
|
104
125
|
|
105
126
|
return if pairs.empty?
|
106
127
|
|
128
|
+
on_hash_for_mixed_shorthand(node)
|
129
|
+
|
107
130
|
if style == :hash_rockets || force_hash_rockets?(pairs)
|
108
131
|
hash_rockets_check(pairs)
|
109
132
|
elsif style == :ruby19_no_mixed_keys
|
@@ -187,7 +210,7 @@ module RuboCop
|
|
187
210
|
return true if /\A[_a-z]\w*[?!]?\z/i.match?(sym_name)
|
188
211
|
|
189
212
|
# For more complicated hash keys, let the parser validate the syntax.
|
190
|
-
|
213
|
+
parse("{ #{sym_name}: :foo }").valid_syntax?
|
191
214
|
end
|
192
215
|
|
193
216
|
def check(pairs, delim, msg)
|
@@ -227,13 +250,14 @@ module RuboCop
|
|
227
250
|
end
|
228
251
|
|
229
252
|
def argument_without_space?(node)
|
230
|
-
node.argument? && node.
|
253
|
+
node.argument? && node.source_range.begin_pos == node.parent.loc.selector.end_pos
|
231
254
|
end
|
232
255
|
|
233
256
|
def autocorrect_hash_rockets(corrector, pair_node)
|
234
257
|
op = pair_node.loc.operator
|
235
258
|
|
236
259
|
key_with_hash_rocket = ":#{pair_node.key.source}#{pair_node.inverse_delimiter(true)}"
|
260
|
+
key_with_hash_rocket += pair_node.key.source if pair_node.value_omission?
|
237
261
|
corrector.replace(pair_node.key, key_with_hash_rocket)
|
238
262
|
corrector.remove(range_with_surrounding_space(op))
|
239
263
|
end
|
@@ -136,6 +136,7 @@ module RuboCop
|
|
136
136
|
|
137
137
|
private
|
138
138
|
|
139
|
+
# rubocop:disable Metrics/CyclomaticComplexity, Metrics/PerceivedComplexity
|
139
140
|
def check_branches(node, branches)
|
140
141
|
# return if any branch is empty. An empty branch can be an `if`
|
141
142
|
# without an `else` or a branch that contains only comments.
|
@@ -144,9 +145,13 @@ module RuboCop
|
|
144
145
|
tails = branches.map { |branch| tail(branch) }
|
145
146
|
check_expressions(node, tails, :after_condition) if duplicated_expressions?(node, tails)
|
146
147
|
|
148
|
+
return if last_child_of_parent?(node) &&
|
149
|
+
branches.any? { |branch| single_child_branch?(branch) }
|
150
|
+
|
147
151
|
heads = branches.map { |branch| head(branch) }
|
148
152
|
check_expressions(node, heads, :before_condition) if duplicated_expressions?(node, heads)
|
149
153
|
end
|
154
|
+
# rubocop:enable Metrics/CyclomaticComplexity, Metrics/PerceivedComplexity
|
150
155
|
|
151
156
|
def duplicated_expressions?(node, expressions)
|
152
157
|
unique_expressions = expressions.uniq
|
@@ -180,6 +185,16 @@ module RuboCop
|
|
180
185
|
end
|
181
186
|
end
|
182
187
|
|
188
|
+
def last_child_of_parent?(node)
|
189
|
+
return true unless (parent = node.parent)
|
190
|
+
|
191
|
+
parent.child_nodes.last == node
|
192
|
+
end
|
193
|
+
|
194
|
+
def single_child_branch?(branch_node)
|
195
|
+
!branch_node.begin_type? || branch_node.children.size == 1
|
196
|
+
end
|
197
|
+
|
183
198
|
def message(node)
|
184
199
|
format(MSG, source: node.source)
|
185
200
|
end
|
@@ -59,11 +59,13 @@ module RuboCop
|
|
59
59
|
# end
|
60
60
|
#
|
61
61
|
class IfInsideElse < Base
|
62
|
+
include IgnoredNode
|
62
63
|
include RangeHelp
|
63
64
|
extend AutoCorrector
|
64
65
|
|
65
66
|
MSG = 'Convert `if` nested inside `else` to `elsif`.'
|
66
67
|
|
68
|
+
# rubocop:disable Metrics/CyclomaticComplexity
|
67
69
|
def on_if(node)
|
68
70
|
return if node.ternary? || node.unless?
|
69
71
|
|
@@ -73,9 +75,13 @@ module RuboCop
|
|
73
75
|
return if allow_if_modifier_in_else_branch?(else_branch)
|
74
76
|
|
75
77
|
add_offense(else_branch.loc.keyword) do |corrector|
|
78
|
+
next if part_of_ignored_node?(node)
|
79
|
+
|
76
80
|
autocorrect(corrector, else_branch)
|
81
|
+
ignore_node(node)
|
77
82
|
end
|
78
83
|
end
|
84
|
+
# rubocop:enable Metrics/CyclomaticComplexity
|
79
85
|
|
80
86
|
private
|
81
87
|
|