rubocop 1.31.1 → 1.52.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (475) hide show
  1. checksums.yaml +4 -4
  2. data/LICENSE.txt +1 -1
  3. data/README.md +5 -5
  4. data/config/default.yml +362 -54
  5. data/config/obsoletion.yml +23 -1
  6. data/exe/rubocop +1 -1
  7. data/lib/rubocop/arguments_env.rb +17 -0
  8. data/lib/rubocop/arguments_file.rb +17 -0
  9. data/lib/rubocop/cache_config.rb +29 -0
  10. data/lib/rubocop/cli/command/{auto_genenerate_config.rb → auto_generate_config.rb} +9 -2
  11. data/lib/rubocop/cli/command/execute_runner.rb +14 -9
  12. data/lib/rubocop/cli/command/init_dotfile.rb +1 -1
  13. data/lib/rubocop/cli/command/suggest_extensions.rb +61 -16
  14. data/lib/rubocop/cli.rb +56 -9
  15. data/lib/rubocop/comment_config.rb +60 -1
  16. data/lib/rubocop/config.rb +48 -20
  17. data/lib/rubocop/config_finder.rb +68 -0
  18. data/lib/rubocop/config_loader.rb +46 -68
  19. data/lib/rubocop/config_loader_resolver.rb +11 -12
  20. data/lib/rubocop/config_obsoletion/changed_parameter.rb +5 -0
  21. data/lib/rubocop/config_obsoletion/parameter_rule.rb +4 -0
  22. data/lib/rubocop/config_obsoletion.rb +9 -4
  23. data/lib/rubocop/config_validator.rb +1 -1
  24. data/lib/rubocop/cop/autocorrect_logic.rb +29 -13
  25. data/lib/rubocop/cop/badge.rb +9 -4
  26. data/lib/rubocop/cop/base.rb +116 -84
  27. data/lib/rubocop/cop/bundler/gem_comment.rb +1 -1
  28. data/lib/rubocop/cop/commissioner.rb +19 -6
  29. data/lib/rubocop/cop/cop.rb +54 -34
  30. data/lib/rubocop/cop/corrector.rb +31 -11
  31. data/lib/rubocop/cop/correctors/alignment_corrector.rb +3 -3
  32. data/lib/rubocop/cop/correctors/each_to_for_corrector.rb +3 -3
  33. data/lib/rubocop/cop/correctors/for_to_each_corrector.rb +3 -3
  34. data/lib/rubocop/cop/correctors/line_break_corrector.rb +1 -1
  35. data/lib/rubocop/cop/correctors/multiline_literal_brace_corrector.rb +23 -7
  36. data/lib/rubocop/cop/correctors/ordered_gem_corrector.rb +2 -7
  37. data/lib/rubocop/cop/correctors/parentheses_corrector.rb +58 -0
  38. data/lib/rubocop/cop/correctors/percent_literal_corrector.rb +2 -2
  39. data/lib/rubocop/cop/gemspec/dependency_version.rb +17 -19
  40. data/lib/rubocop/cop/gemspec/deprecated_attribute_assignment.rb +1 -1
  41. data/lib/rubocop/cop/gemspec/development_dependencies.rb +107 -0
  42. data/lib/rubocop/cop/gemspec/require_mfa.rb +1 -1
  43. data/lib/rubocop/cop/generator/require_file_injector.rb +2 -2
  44. data/lib/rubocop/cop/generator.rb +5 -2
  45. data/lib/rubocop/cop/internal_affairs/cop_description.rb +38 -12
  46. data/lib/rubocop/cop/internal_affairs/create_empty_file.rb +37 -0
  47. data/lib/rubocop/cop/internal_affairs/example_heredoc_delimiter.rb +111 -0
  48. data/lib/rubocop/cop/internal_affairs/inherit_deprecated_cop_class.rb +1 -1
  49. data/lib/rubocop/cop/internal_affairs/lambda_or_proc.rb +46 -0
  50. data/lib/rubocop/cop/internal_affairs/location_expression.rb +37 -0
  51. data/lib/rubocop/cop/internal_affairs/node_matcher_directive.rb +3 -3
  52. data/lib/rubocop/cop/internal_affairs/node_type_predicate.rb +1 -1
  53. data/lib/rubocop/cop/internal_affairs/numblock_handler.rb +69 -0
  54. data/lib/rubocop/cop/internal_affairs/processed_source_buffer_name.rb +42 -0
  55. data/lib/rubocop/cop/internal_affairs/redundant_let_rubocop_config_new.rb +11 -3
  56. data/lib/rubocop/cop/internal_affairs/redundant_location_argument.rb +1 -1
  57. data/lib/rubocop/cop/internal_affairs/redundant_message_argument.rb +1 -1
  58. data/lib/rubocop/cop/internal_affairs/redundant_source_range.rb +66 -0
  59. data/lib/rubocop/cop/internal_affairs/single_line_comparison.rb +62 -0
  60. data/lib/rubocop/cop/internal_affairs/useless_restrict_on_send.rb +60 -0
  61. data/lib/rubocop/cop/internal_affairs.rb +9 -0
  62. data/lib/rubocop/cop/layout/array_alignment.rb +1 -1
  63. data/lib/rubocop/cop/layout/block_alignment.rb +16 -12
  64. data/lib/rubocop/cop/layout/block_end_newline.rb +31 -9
  65. data/lib/rubocop/cop/layout/class_structure.rb +37 -27
  66. data/lib/rubocop/cop/layout/closing_heredoc_indentation.rb +1 -2
  67. data/lib/rubocop/cop/layout/closing_parenthesis_indentation.rb +2 -6
  68. data/lib/rubocop/cop/layout/comment_indentation.rb +3 -1
  69. data/lib/rubocop/cop/layout/empty_comment.rb +3 -3
  70. data/lib/rubocop/cop/layout/empty_line_between_defs.rb +1 -1
  71. data/lib/rubocop/cop/layout/empty_lines.rb +3 -1
  72. data/lib/rubocop/cop/layout/empty_lines_around_access_modifier.rb +7 -2
  73. data/lib/rubocop/cop/layout/empty_lines_around_block_body.rb +2 -0
  74. data/lib/rubocop/cop/layout/end_alignment.rb +9 -1
  75. data/lib/rubocop/cop/layout/end_of_line.rb +4 -4
  76. data/lib/rubocop/cop/layout/extra_spacing.rb +15 -6
  77. data/lib/rubocop/cop/layout/first_argument_indentation.rb +15 -4
  78. data/lib/rubocop/cop/layout/first_array_element_indentation.rb +6 -5
  79. data/lib/rubocop/cop/layout/first_array_element_line_break.rb +35 -8
  80. data/lib/rubocop/cop/layout/first_hash_element_indentation.rb +5 -5
  81. data/lib/rubocop/cop/layout/first_hash_element_line_break.rb +36 -1
  82. data/lib/rubocop/cop/layout/first_method_argument_line_break.rb +57 -8
  83. data/lib/rubocop/cop/layout/first_method_parameter_line_break.rb +52 -19
  84. data/lib/rubocop/cop/layout/heredoc_argument_closing_parenthesis.rb +10 -4
  85. data/lib/rubocop/cop/layout/heredoc_indentation.rb +8 -11
  86. data/lib/rubocop/cop/layout/indentation_style.rb +7 -2
  87. data/lib/rubocop/cop/layout/indentation_width.rb +6 -2
  88. data/lib/rubocop/cop/layout/initial_indentation.rb +1 -1
  89. data/lib/rubocop/cop/layout/leading_comment_space.rb +1 -1
  90. data/lib/rubocop/cop/layout/line_continuation_leading_space.rb +80 -12
  91. data/lib/rubocop/cop/layout/line_continuation_spacing.rb +18 -8
  92. data/lib/rubocop/cop/layout/line_length.rb +8 -1
  93. data/lib/rubocop/cop/layout/multiline_array_line_breaks.rb +31 -1
  94. data/lib/rubocop/cop/layout/multiline_assignment_layout.rb +1 -1
  95. data/lib/rubocop/cop/layout/multiline_block_layout.rb +3 -1
  96. data/lib/rubocop/cop/layout/multiline_hash_key_line_breaks.rb +29 -1
  97. data/lib/rubocop/cop/layout/multiline_method_argument_line_breaks.rb +39 -2
  98. data/lib/rubocop/cop/layout/multiline_method_parameter_line_breaks.rb +77 -0
  99. data/lib/rubocop/cop/layout/redundant_line_break.rb +9 -10
  100. data/lib/rubocop/cop/layout/rescue_ensure_alignment.rb +2 -2
  101. data/lib/rubocop/cop/layout/space_around_block_parameters.rb +1 -1
  102. data/lib/rubocop/cop/layout/space_around_keyword.rb +3 -3
  103. data/lib/rubocop/cop/layout/space_around_operators.rb +1 -1
  104. data/lib/rubocop/cop/layout/space_before_block_braces.rb +2 -0
  105. data/lib/rubocop/cop/layout/space_before_first_arg.rb +1 -1
  106. data/lib/rubocop/cop/layout/space_in_lambda_literal.rb +2 -2
  107. data/lib/rubocop/cop/layout/space_inside_array_literal_brackets.rb +22 -20
  108. data/lib/rubocop/cop/layout/space_inside_array_percent_literal.rb +3 -0
  109. data/lib/rubocop/cop/layout/space_inside_block_braces.rb +27 -9
  110. data/lib/rubocop/cop/layout/space_inside_hash_literal_braces.rb +30 -3
  111. data/lib/rubocop/cop/layout/space_inside_parens.rb +2 -2
  112. data/lib/rubocop/cop/layout/space_inside_percent_literal_delimiters.rb +34 -0
  113. data/lib/rubocop/cop/layout/space_inside_reference_brackets.rb +10 -6
  114. data/lib/rubocop/cop/layout/space_inside_string_interpolation.rb +5 -4
  115. data/lib/rubocop/cop/layout/trailing_empty_lines.rb +1 -1
  116. data/lib/rubocop/cop/layout/trailing_whitespace.rb +12 -5
  117. data/lib/rubocop/cop/legacy/corrections_proxy.rb +1 -1
  118. data/lib/rubocop/cop/legacy/corrector.rb +1 -1
  119. data/lib/rubocop/cop/lint/ambiguous_block_association.rb +40 -8
  120. data/lib/rubocop/cop/lint/ambiguous_operator.rb +4 -0
  121. data/lib/rubocop/cop/lint/assignment_in_condition.rb +11 -1
  122. data/lib/rubocop/cop/lint/constant_resolution.rb +5 -1
  123. data/lib/rubocop/cop/lint/debugger.rb +27 -31
  124. data/lib/rubocop/cop/lint/deprecated_class_methods.rb +66 -110
  125. data/lib/rubocop/cop/lint/deprecated_constants.rb +8 -1
  126. data/lib/rubocop/cop/lint/deprecated_open_ssl_constant.rb +1 -1
  127. data/lib/rubocop/cop/lint/duplicate_branch.rb +0 -2
  128. data/lib/rubocop/cop/lint/duplicate_magic_comment.rb +73 -0
  129. data/lib/rubocop/cop/lint/duplicate_match_pattern.rb +122 -0
  130. data/lib/rubocop/cop/lint/duplicate_methods.rb +48 -18
  131. data/lib/rubocop/cop/lint/duplicate_regexp_character_class_element.rb +26 -9
  132. data/lib/rubocop/cop/lint/duplicate_require.rb +1 -1
  133. data/lib/rubocop/cop/lint/else_layout.rb +3 -7
  134. data/lib/rubocop/cop/lint/empty_block.rb +3 -7
  135. data/lib/rubocop/cop/lint/empty_class.rb +3 -1
  136. data/lib/rubocop/cop/lint/empty_conditional_body.rb +110 -2
  137. data/lib/rubocop/cop/lint/empty_interpolation.rb +1 -1
  138. data/lib/rubocop/cop/lint/erb_new_arguments.rb +12 -13
  139. data/lib/rubocop/cop/lint/format_parameter_mismatch.rb +14 -7
  140. data/lib/rubocop/cop/lint/heredoc_method_call_position.rb +15 -17
  141. data/lib/rubocop/cop/lint/identity_comparison.rb +0 -1
  142. data/lib/rubocop/cop/lint/implicit_string_concatenation.rb +1 -1
  143. data/lib/rubocop/cop/lint/incompatible_io_select_with_fiber_scheduler.rb +5 -3
  144. data/lib/rubocop/cop/lint/ineffective_access_modifier.rb +1 -1
  145. data/lib/rubocop/cop/lint/inherit_exception.rb +9 -0
  146. data/lib/rubocop/cop/lint/interpolation_check.rb +4 -3
  147. data/lib/rubocop/cop/lint/lambda_without_literal_block.rb +1 -1
  148. data/lib/rubocop/cop/lint/literal_in_interpolation.rb +48 -2
  149. data/lib/rubocop/cop/lint/missing_cop_enable_directive.rb +18 -3
  150. data/lib/rubocop/cop/lint/missing_super.rb +34 -2
  151. data/lib/rubocop/cop/lint/mixed_regexp_capture_types.rb +1 -0
  152. data/lib/rubocop/cop/lint/nested_method_definition.rb +53 -9
  153. data/lib/rubocop/cop/lint/next_without_accumulator.rb +25 -6
  154. data/lib/rubocop/cop/lint/non_atomic_file_operation.rb +68 -28
  155. data/lib/rubocop/cop/lint/non_deterministic_require_order.rb +12 -0
  156. data/lib/rubocop/cop/lint/number_conversion.rb +28 -6
  157. data/lib/rubocop/cop/lint/numbered_parameter_assignment.rb +2 -2
  158. data/lib/rubocop/cop/lint/or_assignment_to_constant.rb +2 -0
  159. data/lib/rubocop/cop/lint/ordered_magic_comments.rb +4 -6
  160. data/lib/rubocop/cop/lint/out_of_range_regexp_ref.rb +17 -2
  161. data/lib/rubocop/cop/lint/parentheses_as_grouped_expression.rb +5 -0
  162. data/lib/rubocop/cop/lint/percent_string_array.rb +1 -1
  163. data/lib/rubocop/cop/lint/percent_symbol_array.rb +1 -1
  164. data/lib/rubocop/cop/lint/redundant_cop_disable_directive.rb +49 -9
  165. data/lib/rubocop/cop/lint/redundant_cop_enable_directive.rb +6 -6
  166. data/lib/rubocop/cop/lint/redundant_dir_glob_sort.rb +7 -0
  167. data/lib/rubocop/cop/lint/redundant_require_statement.rb +48 -10
  168. data/lib/rubocop/cop/lint/redundant_safe_navigation.rb +13 -0
  169. data/lib/rubocop/cop/lint/redundant_splat_expansion.rb +1 -1
  170. data/lib/rubocop/cop/lint/redundant_string_coercion.rb +35 -15
  171. data/lib/rubocop/cop/lint/redundant_with_index.rb +14 -11
  172. data/lib/rubocop/cop/lint/redundant_with_object.rb +13 -12
  173. data/lib/rubocop/cop/lint/refinement_import_methods.rb +2 -1
  174. data/lib/rubocop/cop/lint/regexp_as_condition.rb +6 -0
  175. data/lib/rubocop/cop/lint/require_parentheses.rb +3 -1
  176. data/lib/rubocop/cop/lint/require_range_parentheses.rb +57 -0
  177. data/lib/rubocop/cop/lint/rescue_type.rb +3 -3
  178. data/lib/rubocop/cop/lint/safe_navigation_chain.rb +41 -8
  179. data/lib/rubocop/cop/lint/safe_navigation_consistency.rb +1 -1
  180. data/lib/rubocop/cop/lint/script_permission.rb +1 -1
  181. data/lib/rubocop/cop/lint/send_with_mixin_argument.rb +6 -6
  182. data/lib/rubocop/cop/lint/shadowed_exception.rb +21 -22
  183. data/lib/rubocop/cop/lint/shadowing_outer_local_variable.rb +28 -3
  184. data/lib/rubocop/cop/lint/suppressed_exception.rb +1 -1
  185. data/lib/rubocop/cop/lint/syntax.rb +4 -0
  186. data/lib/rubocop/cop/lint/to_enum_arguments.rb +13 -3
  187. data/lib/rubocop/cop/lint/top_level_return_with_argument.rb +23 -9
  188. data/lib/rubocop/cop/lint/unreachable_loop.rb +12 -6
  189. data/lib/rubocop/cop/lint/unused_method_argument.rb +6 -1
  190. data/lib/rubocop/cop/lint/useless_access_modifier.rb +17 -12
  191. data/lib/rubocop/cop/lint/useless_assignment.rb +59 -1
  192. data/lib/rubocop/cop/lint/useless_method_definition.rb +12 -4
  193. data/lib/rubocop/cop/lint/useless_rescue.rb +89 -0
  194. data/lib/rubocop/cop/lint/useless_ruby2_keywords.rb +15 -5
  195. data/lib/rubocop/cop/lint/useless_times.rb +1 -1
  196. data/lib/rubocop/cop/lint/void.rb +92 -21
  197. data/lib/rubocop/cop/metrics/abc_size.rb +4 -2
  198. data/lib/rubocop/cop/metrics/block_length.rb +16 -11
  199. data/lib/rubocop/cop/metrics/block_nesting.rb +2 -2
  200. data/lib/rubocop/cop/metrics/class_length.rb +11 -5
  201. data/lib/rubocop/cop/metrics/collection_literal_length.rb +76 -0
  202. data/lib/rubocop/cop/metrics/cyclomatic_complexity.rb +1 -1
  203. data/lib/rubocop/cop/metrics/method_length.rb +17 -11
  204. data/lib/rubocop/cop/metrics/module_length.rb +10 -5
  205. data/lib/rubocop/cop/metrics/parameter_lists.rb +27 -0
  206. data/lib/rubocop/cop/metrics/perceived_complexity.rb +1 -1
  207. data/lib/rubocop/cop/metrics/utils/abc_size_calculator.rb +4 -8
  208. data/lib/rubocop/cop/metrics/utils/code_length_calculator.rb +9 -6
  209. data/lib/rubocop/cop/migration/department_name.rb +1 -1
  210. data/lib/rubocop/cop/mixin/alignment.rb +2 -2
  211. data/lib/rubocop/cop/mixin/allowed_identifiers.rb +2 -2
  212. data/lib/rubocop/cop/mixin/allowed_methods.rb +23 -2
  213. data/lib/rubocop/cop/mixin/allowed_pattern.rb +17 -1
  214. data/lib/rubocop/cop/mixin/allowed_receivers.rb +34 -0
  215. data/lib/rubocop/cop/mixin/annotation_comment.rb +14 -7
  216. data/lib/rubocop/cop/mixin/check_line_breakable.rb +5 -1
  217. data/lib/rubocop/cop/mixin/code_length.rb +1 -1
  218. data/lib/rubocop/cop/mixin/comments_help.rb +29 -7
  219. data/lib/rubocop/cop/mixin/configurable_enforced_style.rb +21 -9
  220. data/lib/rubocop/cop/mixin/def_node.rb +2 -7
  221. data/lib/rubocop/cop/mixin/documentation_comment.rb +1 -1
  222. data/lib/rubocop/cop/mixin/enforce_superclass.rb +2 -1
  223. data/lib/rubocop/cop/mixin/first_element_line_break.rb +11 -7
  224. data/lib/rubocop/cop/mixin/frozen_string_literal.rb +4 -0
  225. data/lib/rubocop/cop/mixin/hash_alignment_styles.rb +1 -1
  226. data/lib/rubocop/cop/mixin/hash_shorthand_syntax.rb +152 -12
  227. data/lib/rubocop/cop/mixin/hash_transform_method.rb +13 -9
  228. data/lib/rubocop/cop/mixin/line_length_help.rb +11 -2
  229. data/lib/rubocop/cop/mixin/method_complexity.rb +13 -16
  230. data/lib/rubocop/cop/mixin/min_branches_count.rb +40 -0
  231. data/lib/rubocop/cop/mixin/multiline_element_indentation.rb +7 -14
  232. data/lib/rubocop/cop/mixin/multiline_element_line_breaks.rb +5 -6
  233. data/lib/rubocop/cop/mixin/ordered_gem_node.rb +1 -1
  234. data/lib/rubocop/cop/mixin/percent_array.rb +58 -1
  235. data/lib/rubocop/cop/mixin/preceding_following_alignment.rb +1 -1
  236. data/lib/rubocop/cop/mixin/range_help.rb +22 -5
  237. data/lib/rubocop/cop/mixin/require_library.rb +2 -0
  238. data/lib/rubocop/cop/mixin/rescue_node.rb +5 -3
  239. data/lib/rubocop/cop/mixin/space_after_punctuation.rb +1 -1
  240. data/lib/rubocop/cop/mixin/statement_modifier.rb +18 -3
  241. data/lib/rubocop/cop/mixin/surrounding_space.rb +13 -11
  242. data/lib/rubocop/cop/mixin/trailing_comma.rb +2 -2
  243. data/lib/rubocop/cop/mixin/visibility_help.rb +40 -5
  244. data/lib/rubocop/cop/naming/ascii_identifiers.rb +1 -1
  245. data/lib/rubocop/cop/naming/block_forwarding.rb +5 -1
  246. data/lib/rubocop/cop/naming/block_parameter_name.rb +1 -1
  247. data/lib/rubocop/cop/naming/class_and_module_camel_case.rb +3 -1
  248. data/lib/rubocop/cop/naming/constant_name.rb +3 -3
  249. data/lib/rubocop/cop/naming/heredoc_delimiter_case.rb +1 -1
  250. data/lib/rubocop/cop/naming/inclusive_language.rb +28 -6
  251. data/lib/rubocop/cop/naming/memoized_instance_variable_name.rb +22 -7
  252. data/lib/rubocop/cop/naming/method_name.rb +3 -3
  253. data/lib/rubocop/cop/naming/predicate_name.rb +31 -2
  254. data/lib/rubocop/cop/naming/rescued_exceptions_variable_name.rb +12 -4
  255. data/lib/rubocop/cop/naming/variable_name.rb +6 -1
  256. data/lib/rubocop/cop/registry.rb +73 -45
  257. data/lib/rubocop/cop/security/compound_hash.rb +2 -1
  258. data/lib/rubocop/cop/style/access_modifier_declarations.rb +92 -3
  259. data/lib/rubocop/cop/style/accessor_grouping.rb +50 -20
  260. data/lib/rubocop/cop/style/alias.rb +9 -1
  261. data/lib/rubocop/cop/style/arguments_forwarding.rb +6 -5
  262. data/lib/rubocop/cop/style/array_intersect.rb +111 -0
  263. data/lib/rubocop/cop/style/ascii_comments.rb +1 -1
  264. data/lib/rubocop/cop/style/attr.rb +11 -1
  265. data/lib/rubocop/cop/style/begin_block.rb +1 -2
  266. data/lib/rubocop/cop/style/bisected_attr_accessor.rb +1 -1
  267. data/lib/rubocop/cop/style/block_comments.rb +2 -2
  268. data/lib/rubocop/cop/style/block_delimiters.rb +44 -10
  269. data/lib/rubocop/cop/style/case_equality.rb +40 -10
  270. data/lib/rubocop/cop/style/case_like_if.rb +20 -3
  271. data/lib/rubocop/cop/style/character_literal.rb +1 -1
  272. data/lib/rubocop/cop/style/class_and_module_children.rb +9 -16
  273. data/lib/rubocop/cop/style/class_equality_comparison.rb +72 -12
  274. data/lib/rubocop/cop/style/class_methods_definitions.rb +2 -1
  275. data/lib/rubocop/cop/style/collection_compact.rb +27 -5
  276. data/lib/rubocop/cop/style/collection_methods.rb +2 -0
  277. data/lib/rubocop/cop/style/colon_method_call.rb +2 -2
  278. data/lib/rubocop/cop/style/combinable_loops.rb +29 -7
  279. data/lib/rubocop/cop/style/command_literal.rb +1 -1
  280. data/lib/rubocop/cop/style/comment_annotation.rb +1 -1
  281. data/lib/rubocop/cop/style/commented_keyword.rb +2 -2
  282. data/lib/rubocop/cop/style/comparable_clamp.rb +125 -0
  283. data/lib/rubocop/cop/style/concat_array_literals.rb +94 -0
  284. data/lib/rubocop/cop/style/conditional_assignment.rb +8 -14
  285. data/lib/rubocop/cop/style/copyright.rb +6 -3
  286. data/lib/rubocop/cop/style/data_inheritance.rb +75 -0
  287. data/lib/rubocop/cop/style/dir.rb +1 -1
  288. data/lib/rubocop/cop/style/dir_empty.rb +54 -0
  289. data/lib/rubocop/cop/style/disable_cops_within_source_code_directive.rb +2 -2
  290. data/lib/rubocop/cop/style/document_dynamic_eval_definition.rb +2 -2
  291. data/lib/rubocop/cop/style/documentation.rb +22 -10
  292. data/lib/rubocop/cop/style/documentation_method.rb +10 -4
  293. data/lib/rubocop/cop/style/double_negation.rb +4 -2
  294. data/lib/rubocop/cop/style/each_for_simple_loop.rb +41 -6
  295. data/lib/rubocop/cop/style/each_with_object.rb +40 -9
  296. data/lib/rubocop/cop/style/empty_block_parameter.rb +2 -2
  297. data/lib/rubocop/cop/style/empty_else.rb +37 -0
  298. data/lib/rubocop/cop/style/empty_heredoc.rb +73 -0
  299. data/lib/rubocop/cop/style/empty_lambda_parameter.rb +2 -2
  300. data/lib/rubocop/cop/style/empty_method.rb +1 -1
  301. data/lib/rubocop/cop/style/endless_method.rb +1 -1
  302. data/lib/rubocop/cop/style/eval_with_location.rb +8 -8
  303. data/lib/rubocop/cop/style/exact_regexp_match.rb +68 -0
  304. data/lib/rubocop/cop/style/explicit_block_argument.rb +5 -1
  305. data/lib/rubocop/cop/style/fetch_env_var.rb +10 -177
  306. data/lib/rubocop/cop/style/file_empty.rb +71 -0
  307. data/lib/rubocop/cop/style/file_read.rb +3 -3
  308. data/lib/rubocop/cop/style/file_write.rb +1 -1
  309. data/lib/rubocop/cop/style/for.rb +2 -0
  310. data/lib/rubocop/cop/style/format_string_token.rb +25 -6
  311. data/lib/rubocop/cop/style/frozen_string_literal_comment.rb +1 -1
  312. data/lib/rubocop/cop/style/guard_clause.rb +127 -38
  313. data/lib/rubocop/cop/style/hash_as_last_array_item.rb +1 -0
  314. data/lib/rubocop/cop/style/hash_each_methods.rb +36 -21
  315. data/lib/rubocop/cop/style/hash_except.rb +27 -16
  316. data/lib/rubocop/cop/style/hash_like_case.rb +3 -9
  317. data/lib/rubocop/cop/style/hash_syntax.rb +26 -2
  318. data/lib/rubocop/cop/style/hash_transform_keys.rb +2 -2
  319. data/lib/rubocop/cop/style/hash_transform_values.rb +2 -2
  320. data/lib/rubocop/cop/style/identical_conditional_branches.rb +15 -0
  321. data/lib/rubocop/cop/style/if_inside_else.rb +6 -0
  322. data/lib/rubocop/cop/style/if_unless_modifier.rb +112 -16
  323. data/lib/rubocop/cop/style/if_with_boolean_literal_branches.rb +29 -2
  324. data/lib/rubocop/cop/style/if_with_semicolon.rb +4 -4
  325. data/lib/rubocop/cop/style/infinite_loop.rb +2 -5
  326. data/lib/rubocop/cop/style/inverse_methods.rb +15 -11
  327. data/lib/rubocop/cop/style/invertible_unless_condition.rb +118 -0
  328. data/lib/rubocop/cop/style/line_end_concatenation.rb +4 -1
  329. data/lib/rubocop/cop/style/magic_comment_format.rb +307 -0
  330. data/lib/rubocop/cop/style/map_compact_with_conditional_block.rb +2 -2
  331. data/lib/rubocop/cop/style/map_to_hash.rb +4 -1
  332. data/lib/rubocop/cop/style/map_to_set.rb +64 -0
  333. data/lib/rubocop/cop/style/method_call_with_args_parentheses/omit_parentheses.rb +41 -26
  334. data/lib/rubocop/cop/style/method_call_with_args_parentheses/require_parentheses.rb +5 -1
  335. data/lib/rubocop/cop/style/method_call_with_args_parentheses.rb +48 -41
  336. data/lib/rubocop/cop/style/method_call_without_args_parentheses.rb +21 -2
  337. data/lib/rubocop/cop/style/method_called_on_do_end_block.rb +4 -1
  338. data/lib/rubocop/cop/style/method_def_parentheses.rb +11 -4
  339. data/lib/rubocop/cop/style/min_max.rb +3 -3
  340. data/lib/rubocop/cop/style/min_max_comparison.rb +83 -0
  341. data/lib/rubocop/cop/style/missing_else.rb +13 -1
  342. data/lib/rubocop/cop/style/mixin_grouping.rb +4 -4
  343. data/lib/rubocop/cop/style/module_function.rb +30 -8
  344. data/lib/rubocop/cop/style/multiline_block_chain.rb +3 -1
  345. data/lib/rubocop/cop/style/multiline_if_modifier.rb +0 -4
  346. data/lib/rubocop/cop/style/multiline_in_pattern_then.rb +1 -1
  347. data/lib/rubocop/cop/style/multiline_memoization.rb +2 -2
  348. data/lib/rubocop/cop/style/multiline_method_signature.rb +7 -4
  349. data/lib/rubocop/cop/style/multiline_ternary_operator.rb +18 -3
  350. data/lib/rubocop/cop/style/multiple_comparison.rb +14 -0
  351. data/lib/rubocop/cop/style/negated_if_else_condition.rb +17 -10
  352. data/lib/rubocop/cop/style/nested_parenthesized_calls.rb +9 -0
  353. data/lib/rubocop/cop/style/next.rb +3 -5
  354. data/lib/rubocop/cop/style/nil_lambda.rb +4 -4
  355. data/lib/rubocop/cop/style/numbered_parameters_limit.rb +11 -3
  356. data/lib/rubocop/cop/style/numeric_literals.rb +16 -1
  357. data/lib/rubocop/cop/style/numeric_predicate.rb +43 -9
  358. data/lib/rubocop/cop/style/object_then.rb +5 -0
  359. data/lib/rubocop/cop/style/one_line_conditional.rb +3 -6
  360. data/lib/rubocop/cop/style/operator_method_call.rb +67 -0
  361. data/lib/rubocop/cop/style/parallel_assignment.rb +29 -19
  362. data/lib/rubocop/cop/style/percent_literal_delimiters.rb +2 -3
  363. data/lib/rubocop/cop/style/percent_q_literals.rb +1 -1
  364. data/lib/rubocop/cop/style/perl_backrefs.rb +22 -1
  365. data/lib/rubocop/cop/style/proc.rb +4 -1
  366. data/lib/rubocop/cop/style/quoted_symbols.rb +1 -1
  367. data/lib/rubocop/cop/style/redundant_argument.rb +3 -0
  368. data/lib/rubocop/cop/style/redundant_array_constructor.rb +77 -0
  369. data/lib/rubocop/cop/style/redundant_begin.rb +3 -0
  370. data/lib/rubocop/cop/style/redundant_condition.rb +41 -8
  371. data/lib/rubocop/cop/style/redundant_conditional.rb +0 -4
  372. data/lib/rubocop/cop/style/redundant_constant_base.rb +85 -0
  373. data/lib/rubocop/cop/style/redundant_double_splat_hash_braces.rb +45 -0
  374. data/lib/rubocop/cop/style/redundant_each.rb +116 -0
  375. data/lib/rubocop/cop/style/redundant_fetch_block.rb +7 -5
  376. data/lib/rubocop/cop/style/redundant_filter_chain.rb +101 -0
  377. data/lib/rubocop/cop/style/redundant_heredoc_delimiter_quotes.rb +58 -0
  378. data/lib/rubocop/cop/style/redundant_initialize.rb +3 -1
  379. data/lib/rubocop/cop/style/redundant_interpolation.rb +2 -2
  380. data/lib/rubocop/cop/style/redundant_line_continuation.rb +183 -0
  381. data/lib/rubocop/cop/style/redundant_parentheses.rb +22 -24
  382. data/lib/rubocop/cop/style/redundant_percent_q.rb +1 -1
  383. data/lib/rubocop/cop/style/redundant_regexp_character_class.rb +9 -3
  384. data/lib/rubocop/cop/style/redundant_regexp_constructor.rb +46 -0
  385. data/lib/rubocop/cop/style/redundant_regexp_escape.rb +21 -4
  386. data/lib/rubocop/cop/style/redundant_return.rb +7 -0
  387. data/lib/rubocop/cop/style/redundant_self.rb +2 -0
  388. data/lib/rubocop/cop/style/redundant_sort.rb +24 -9
  389. data/lib/rubocop/cop/style/redundant_sort_by.rb +24 -8
  390. data/lib/rubocop/cop/style/redundant_string_escape.rb +183 -0
  391. data/lib/rubocop/cop/style/regexp_literal.rb +11 -2
  392. data/lib/rubocop/cop/style/require_order.rb +139 -0
  393. data/lib/rubocop/cop/style/rescue_modifier.rb +2 -4
  394. data/lib/rubocop/cop/style/rescue_standard_error.rb +2 -2
  395. data/lib/rubocop/cop/style/safe_navigation.rb +41 -10
  396. data/lib/rubocop/cop/style/select_by_regexp.rb +23 -5
  397. data/lib/rubocop/cop/style/self_assignment.rb +2 -2
  398. data/lib/rubocop/cop/style/semicolon.rb +63 -5
  399. data/lib/rubocop/cop/style/signal_exception.rb +8 -6
  400. data/lib/rubocop/cop/style/single_line_block_params.rb +1 -1
  401. data/lib/rubocop/cop/style/single_line_methods.rb +1 -1
  402. data/lib/rubocop/cop/style/slicing_with_range.rb +1 -1
  403. data/lib/rubocop/cop/style/sole_nested_conditional.rb +20 -9
  404. data/lib/rubocop/cop/style/special_global_vars.rb +3 -4
  405. data/lib/rubocop/cop/style/static_class.rb +32 -1
  406. data/lib/rubocop/cop/style/stderr_puts.rb +1 -1
  407. data/lib/rubocop/cop/style/string_hash_keys.rb +4 -1
  408. data/lib/rubocop/cop/style/string_literals.rb +1 -5
  409. data/lib/rubocop/cop/style/struct_inheritance.rb +1 -1
  410. data/lib/rubocop/cop/style/symbol_array.rb +6 -5
  411. data/lib/rubocop/cop/style/symbol_proc.rb +42 -10
  412. data/lib/rubocop/cop/style/ternary_parentheses.rb +1 -13
  413. data/lib/rubocop/cop/style/top_level_method_definition.rb +3 -1
  414. data/lib/rubocop/cop/style/trailing_body_on_class.rb +1 -0
  415. data/lib/rubocop/cop/style/trailing_comma_in_arguments.rb +4 -4
  416. data/lib/rubocop/cop/style/trailing_comma_in_block_args.rb +1 -1
  417. data/lib/rubocop/cop/style/trailing_underscore_variable.rb +1 -1
  418. data/lib/rubocop/cop/style/trivial_accessors.rb +4 -1
  419. data/lib/rubocop/cop/style/unless_logical_operators.rb +1 -0
  420. data/lib/rubocop/cop/style/unpack_first.rb +3 -3
  421. data/lib/rubocop/cop/style/word_array.rb +59 -5
  422. data/lib/rubocop/cop/style/yoda_condition.rb +13 -6
  423. data/lib/rubocop/cop/style/yoda_expression.rb +90 -0
  424. data/lib/rubocop/cop/style/zero_length_predicate.rb +40 -19
  425. data/lib/rubocop/cop/team.rb +63 -56
  426. data/lib/rubocop/cop/util.rb +44 -8
  427. data/lib/rubocop/cop/variable_force/assignment.rb +34 -2
  428. data/lib/rubocop/cop/variable_force/scope.rb +3 -3
  429. data/lib/rubocop/cop/variable_force/variable.rb +5 -3
  430. data/lib/rubocop/cop/variable_force/variable_table.rb +6 -4
  431. data/lib/rubocop/cop/variable_force.rb +19 -30
  432. data/lib/rubocop/cops_documentation_generator.rb +45 -15
  433. data/lib/rubocop/directive_comment.rb +4 -4
  434. data/lib/rubocop/ext/comment.rb +18 -0
  435. data/lib/rubocop/ext/processed_source.rb +2 -0
  436. data/lib/rubocop/ext/range.rb +15 -0
  437. data/lib/rubocop/ext/regexp_node.rb +1 -1
  438. data/lib/rubocop/ext/regexp_parser.rb +1 -1
  439. data/lib/rubocop/feature_loader.rb +94 -0
  440. data/lib/rubocop/file_patterns.rb +43 -0
  441. data/lib/rubocop/formatter/clang_style_formatter.rb +1 -1
  442. data/lib/rubocop/formatter/disabled_config_formatter.rb +26 -9
  443. data/lib/rubocop/formatter/html_formatter.rb +4 -4
  444. data/lib/rubocop/formatter/junit_formatter.rb +4 -1
  445. data/lib/rubocop/formatter/markdown_formatter.rb +1 -1
  446. data/lib/rubocop/formatter/offense_count_formatter.rb +8 -5
  447. data/lib/rubocop/formatter/simple_text_formatter.rb +1 -1
  448. data/lib/rubocop/formatter/tap_formatter.rb +1 -1
  449. data/lib/rubocop/formatter/worst_offenders_formatter.rb +6 -3
  450. data/lib/rubocop/formatter.rb +4 -1
  451. data/lib/rubocop/options.rb +55 -22
  452. data/lib/rubocop/path_util.rb +50 -22
  453. data/lib/rubocop/rake_task.rb +5 -1
  454. data/lib/rubocop/result_cache.rb +26 -24
  455. data/lib/rubocop/rspec/cop_helper.rb +26 -3
  456. data/lib/rubocop/rspec/expect_offense.rb +6 -4
  457. data/lib/rubocop/rspec/shared_contexts.rb +31 -14
  458. data/lib/rubocop/rspec/support.rb +17 -2
  459. data/lib/rubocop/runner.rb +73 -18
  460. data/lib/rubocop/server/cache.rb +48 -2
  461. data/lib/rubocop/server/cli.rb +62 -19
  462. data/lib/rubocop/server/client_command/base.rb +1 -1
  463. data/lib/rubocop/server/client_command/exec.rb +8 -2
  464. data/lib/rubocop/server/client_command/start.rb +6 -1
  465. data/lib/rubocop/server/core.rb +42 -10
  466. data/lib/rubocop/server/helper.rb +1 -1
  467. data/lib/rubocop/server/server_command/exec.rb +1 -1
  468. data/lib/rubocop/server/socket_reader.rb +5 -1
  469. data/lib/rubocop/server.rb +1 -1
  470. data/lib/rubocop/target_finder.rb +1 -1
  471. data/lib/rubocop/target_ruby.rb +5 -5
  472. data/lib/rubocop/version.rb +17 -7
  473. data/lib/rubocop.rb +49 -9
  474. metadata +65 -36
  475. data/lib/rubocop/cop/mixin/ignored_methods.rb +0 -52
@@ -31,22 +31,26 @@ module RuboCop
31
31
  def on_masgn(node)
32
32
  lhs, rhs = *node
33
33
  lhs_elements = *lhs
34
+ rhs = rhs.body if rhs.rescue_type?
34
35
  rhs_elements = Array(rhs).compact # edge case for one constant
35
36
 
36
37
  return if allowed_lhs?(lhs) || allowed_rhs?(rhs) ||
37
38
  allowed_masign?(lhs_elements, rhs_elements)
38
39
 
39
- add_offense(node) { |corrector| autocorrect(corrector, node) }
40
+ range = node.source_range.begin.join(rhs.source_range.end)
41
+
42
+ add_offense(range) do |corrector|
43
+ autocorrect(corrector, node, lhs, rhs)
44
+ end
40
45
  end
41
46
 
42
47
  private
43
48
 
44
- def autocorrect(corrector, node)
45
- left, right = *node
46
- left_elements = *left
47
- right_elements = Array(right).compact
49
+ def autocorrect(corrector, node, lhs, rhs)
50
+ left_elements = *lhs
51
+ right_elements = Array(rhs).compact
48
52
  order = find_valid_order(left_elements, right_elements)
49
- correction = assignment_corrector(node, order)
53
+ correction = assignment_corrector(node, rhs, order)
50
54
 
51
55
  corrector.replace(correction.correction_range, correction.correction)
52
56
  end
@@ -77,14 +81,19 @@ module RuboCop
77
81
  node.block_type? || node.send_type?
78
82
  end
79
83
 
80
- def assignment_corrector(node, order)
81
- _assignment, modifier = *node.parent
84
+ def assignment_corrector(node, rhs, order)
85
+ if node.parent&.rescue_type?
86
+ _assignment, modifier = *node.parent
87
+ else
88
+ _assignment, modifier = *rhs.parent
89
+ end
90
+
82
91
  if modifier_statement?(node.parent)
83
- ModifierCorrector.new(node, config, order)
92
+ ModifierCorrector.new(node, rhs, modifier, config, order)
84
93
  elsif rescue_modifier?(modifier)
85
- RescueCorrector.new(node, config, order)
94
+ RescueCorrector.new(node, rhs, modifier, config, order)
86
95
  else
87
- GenericCorrector.new(node, config, order)
96
+ GenericCorrector.new(node, rhs, modifier, config, order)
88
97
  end
89
98
  end
90
99
 
@@ -172,17 +181,21 @@ module RuboCop
172
181
  end
173
182
 
174
183
  def modifier_statement?(node)
175
- node && %i[if while until].include?(node.type) && node.modifier_form?
184
+ return false unless node
185
+
186
+ node.basic_conditional? && node.modifier_form?
176
187
  end
177
188
 
178
189
  # An internal class for correcting parallel assignment
179
190
  class GenericCorrector
180
191
  include Alignment
181
192
 
182
- attr_reader :config, :node
193
+ attr_reader :node, :rhs, :rescue_result, :config
183
194
 
184
- def initialize(node, config, new_elements)
195
+ def initialize(node, rhs, modifier, config, new_elements)
185
196
  @node = node
197
+ @rhs = rhs
198
+ _, _, @rescue_result = *modifier
186
199
  @config = config
187
200
  @new_elements = new_elements
188
201
  end
@@ -226,13 +239,10 @@ module RuboCop
226
239
  # protected by rescue
227
240
  class RescueCorrector < GenericCorrector
228
241
  def correction
229
- _node, rescue_clause = *node.parent
230
- _, _, rescue_result = *rescue_clause
231
-
232
242
  # If the parallel assignment uses a rescue modifier and it is the
233
243
  # only contents of a method, then we want to make use of the
234
244
  # implicit begin
235
- if node.parent.parent&.def_type?
245
+ if rhs.parent.parent.parent&.def_type?
236
246
  super + def_correction(rescue_result)
237
247
  else
238
248
  begin_correction(rescue_result)
@@ -240,7 +250,7 @@ module RuboCop
240
250
  end
241
251
 
242
252
  def correction_range
243
- node.parent.source_range
253
+ rhs.parent.parent.source_range
244
254
  end
245
255
 
246
256
  private
@@ -92,9 +92,8 @@ module RuboCop
92
92
 
93
93
  def contains_delimiter?(node, delimiters)
94
94
  delimiters_regexp = Regexp.union(delimiters)
95
- node
96
- .children.map { |n| string_source(n) }.compact
97
- .any? { |s| delimiters_regexp.match?(s) }
95
+
96
+ node.children.filter_map { |n| string_source(n) }.any?(delimiters_regexp)
98
97
  end
99
98
 
100
99
  def string_source(node)
@@ -44,7 +44,7 @@ module RuboCop
44
44
 
45
45
  # Report offense only if changing case doesn't change semantics,
46
46
  # i.e., if the string would become dynamic or has special characters.
47
- ast = ProcessedSource.new(corrected(node.source), target_ruby_version).ast
47
+ ast = parse(corrected(node.source)).ast
48
48
  return if node.children != ast.children
49
49
 
50
50
  add_offense(node.loc.begin) do |corrector|
@@ -83,10 +83,31 @@ module RuboCop
83
83
  end
84
84
  end
85
85
 
86
+ # @private
87
+ # @param [RuboCop::AST::Node] node
88
+ # @return [String, nil]
89
+ def preferred_expression_to_node_with_constant_prefix(node)
90
+ expression = preferred_expression_to(node)
91
+ return unless expression
92
+
93
+ "#{constant_prefix(node)}#{expression}"
94
+ end
95
+
96
+ # @private
97
+ # @param [RuboCop::AST::Node] node
98
+ # @return [String]
99
+ def constant_prefix(node)
100
+ if node.each_ancestor(:class, :module).any?
101
+ '::'
102
+ else
103
+ ''
104
+ end
105
+ end
106
+
86
107
  # @private
87
108
  # @param [RuboCop::AST::Node] node
88
109
  def on_back_ref_or_gvar_or_nth_ref(node)
89
- preferred_expression = preferred_expression_to(node)
110
+ preferred_expression = preferred_expression_to_node_with_constant_prefix(node)
90
111
  return unless preferred_expression
91
112
 
92
113
  add_offense(
@@ -19,7 +19,8 @@ module RuboCop
19
19
  MSG = 'Use `proc` instead of `Proc.new`.'
20
20
 
21
21
  # @!method proc_new?(node)
22
- def_node_matcher :proc_new?, '(block $(send (const {nil? cbase} :Proc) :new) ...)'
22
+ def_node_matcher :proc_new?,
23
+ '({block numblock} $(send (const {nil? cbase} :Proc) :new) ...)'
23
24
 
24
25
  def on_block(node)
25
26
  proc_new?(node) do |block_method|
@@ -28,6 +29,8 @@ module RuboCop
28
29
  end
29
30
  end
30
31
  end
32
+
33
+ alias on_numblock on_block
31
34
  end
32
35
  end
33
36
  end
@@ -93,7 +93,7 @@ module RuboCop
93
93
  end
94
94
 
95
95
  # The conversion process doubles escaped slashes, so they have to be reverted
96
- correction.gsub('\\\\', '\\')
96
+ correction.gsub('\\\\', '\\').gsub('\"', '"')
97
97
  end
98
98
 
99
99
  def style
@@ -13,6 +13,7 @@ module RuboCop
13
13
  # ----
14
14
  # Methods:
15
15
  # join: ''
16
+ # sum: 0
16
17
  # split: ' '
17
18
  # chomp: "\n"
18
19
  # chomp!: "\n"
@@ -33,6 +34,7 @@ module RuboCop
33
34
  # # bad
34
35
  # array.join('')
35
36
  # [1, 2, 3].join("")
37
+ # array.sum(0)
36
38
  # string.split(" ")
37
39
  # "first\nsecond".split(" ")
38
40
  # string.chomp("\n")
@@ -42,6 +44,7 @@ module RuboCop
42
44
  # # good
43
45
  # array.join
44
46
  # [1, 2, 3].join
47
+ # array.sum
45
48
  # string.split
46
49
  # "first second".split
47
50
  # string.chomp
@@ -0,0 +1,77 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RuboCop
4
+ module Cop
5
+ module Style
6
+ # Checks for the instantiation of array using redundant `Array` constructor.
7
+ # Autocorrect replaces to array literal which is the simplest and fastest.
8
+ #
9
+ # @example
10
+ #
11
+ # # bad
12
+ # Array.new([])
13
+ # Array[]
14
+ # Array([])
15
+ # Array.new(['foo', 'foo', 'foo'])
16
+ # Array['foo', 'foo', 'foo']
17
+ # Array(['foo', 'foo', 'foo'])
18
+ #
19
+ # # good
20
+ # []
21
+ # ['foo', 'foo', 'foo']
22
+ # Array.new(3, 'foo')
23
+ # Array.new(3) { 'foo' }
24
+ #
25
+ class RedundantArrayConstructor < Base
26
+ extend AutoCorrector
27
+
28
+ MSG = 'Remove the redundant `Array` constructor.'
29
+
30
+ RESTRICT_ON_SEND = %i[new [] Array].freeze
31
+
32
+ # @!method redundant_array_constructor(node)
33
+ def_node_matcher :redundant_array_constructor, <<~PATTERN
34
+ {
35
+ (send
36
+ (const {nil? cbase} :Array) :new
37
+ $(array ...))
38
+ (send
39
+ (const {nil? cbase} :Array) :[]
40
+ $...)
41
+ (send
42
+ nil? :Array
43
+ $(array ...))
44
+ }
45
+ PATTERN
46
+
47
+ def on_send(node)
48
+ return unless (array_literal = redundant_array_constructor(node))
49
+
50
+ receiver = node.receiver
51
+ selector = node.loc.selector
52
+
53
+ if node.method?(:new)
54
+ range = receiver.source_range.join(selector)
55
+ replacement = array_literal
56
+ elsif node.method?(:Array)
57
+ range = selector
58
+ replacement = array_literal
59
+ else
60
+ range = receiver
61
+ replacement = selector.begin.join(node.source_range.end)
62
+ end
63
+
64
+ register_offense(range, node, replacement)
65
+ end
66
+
67
+ private
68
+
69
+ def register_offense(range, node, replacement)
70
+ add_offense(range) do |corrector|
71
+ corrector.replace(node, replacement.source)
72
+ end
73
+ end
74
+ end
75
+ end
76
+ end
77
+ end
@@ -75,6 +75,7 @@ module RuboCop
75
75
 
76
76
  def on_def(node)
77
77
  return unless node.body&.kwbegin_type?
78
+ return if node.endless? && !node.body.children.one?
78
79
 
79
80
  register_offense(node.body)
80
81
  end
@@ -89,6 +90,8 @@ module RuboCop
89
90
  register_offense(node.body)
90
91
  end
91
92
 
93
+ alias on_numblock on_block
94
+
92
95
  def on_kwbegin(node)
93
96
  return unless (target_node = offensive_kwbegins(node).to_a.last)
94
97
 
@@ -36,6 +36,9 @@ module RuboCop
36
36
 
37
37
  MSG = 'Use double pipes `||` instead.'
38
38
  REDUNDANT_CONDITION = 'This condition is not needed.'
39
+ ARGUMENT_WITH_OPERATOR_TYPES = %i[
40
+ splat block_pass forwarded_restarg forwarded_kwrestarg forwarded_args
41
+ ].freeze
39
42
 
40
43
  def on_if(node)
41
44
  return if node.elsif_conditional?
@@ -67,8 +70,8 @@ module RuboCop
67
70
  end
68
71
 
69
72
  def range_of_offense(node)
70
- return node.loc.expression unless node.ternary?
71
- return node.loc.expression if node.ternary? && branches_have_method?(node)
73
+ return node.source_range unless node.ternary?
74
+ return node.source_range if node.ternary? && branches_have_method?(node)
72
75
 
73
76
  range_between(node.loc.question.begin_pos, node.loc.colon.end_pos)
74
77
  end
@@ -145,25 +148,46 @@ module RuboCop
145
148
 
146
149
  return false unless if_branch && else_branch
147
150
 
148
- if_branch.send_type? && if_branch.arguments.count == 1 &&
149
- else_branch.send_type? && else_branch.arguments.count == 1 &&
151
+ single_argument_method?(if_branch) && single_argument_method?(else_branch) &&
150
152
  same_method?(if_branch, else_branch)
151
153
  end
152
154
 
155
+ def single_argument_method?(node)
156
+ return false if !node.send_type? || node.method?(:[]) || !node.arguments.one?
157
+
158
+ !argument_with_operator?(node.first_argument)
159
+ end
160
+
153
161
  def same_method?(if_branch, else_branch)
154
162
  if_branch.method?(else_branch.method_name) && if_branch.receiver == else_branch.receiver
155
163
  end
156
164
 
157
- def if_source(if_branch)
165
+ # If the argument is using an operator, it is an invalid syntax.
166
+ # e.g. `foo || *bar`, `foo || **bar`, and `foo || &bar`.
167
+ def argument_with_operator?(argument)
168
+ return true if ARGUMENT_WITH_OPERATOR_TYPES.include?(argument.type)
169
+ return false unless argument.hash_type?
170
+ return false unless (node = argument.children.first)
171
+
172
+ node.kwsplat_type? || node.forwarded_kwrestarg_type?
173
+ end
174
+
175
+ def if_source(if_branch, arithmetic_operation)
158
176
  if branches_have_method?(if_branch.parent) && if_branch.parenthesized?
159
177
  if_branch.source.delete_suffix(')')
178
+ elsif arithmetic_operation
179
+ argument_source = if_branch.first_argument.source
180
+
181
+ "#{if_branch.receiver.source} #{if_branch.method_name} (#{argument_source}"
160
182
  else
161
183
  if_branch.source
162
184
  end
163
185
  end
164
186
 
165
- def else_source(else_branch)
166
- if branches_have_method?(else_branch.parent)
187
+ def else_source(else_branch, arithmetic_operation) # rubocop:disable Metrics/AbcSize
188
+ if arithmetic_operation
189
+ "#{else_branch.first_argument.source})"
190
+ elsif branches_have_method?(else_branch.parent)
167
191
  else_source_if_has_method(else_branch)
168
192
  elsif require_parentheses?(else_branch)
169
193
  "(#{else_branch.source})"
@@ -198,7 +222,12 @@ module RuboCop
198
222
 
199
223
  def make_ternary_form(node)
200
224
  _condition, if_branch, else_branch = *node
201
- ternary_form = [if_source(if_branch), else_source(else_branch)].join(' || ')
225
+ arithmetic_operation = use_arithmetic_operation?(if_branch)
226
+
227
+ ternary_form = [
228
+ if_source(if_branch, arithmetic_operation),
229
+ else_source(else_branch, arithmetic_operation)
230
+ ].join(' || ')
202
231
  ternary_form += ')' if branches_have_method?(node) && if_branch.parenthesized?
203
232
 
204
233
  if node.parent&.send_type?
@@ -227,6 +256,10 @@ module RuboCop
227
256
  node.hash_type? && !node.braces?
228
257
  end
229
258
 
259
+ def use_arithmetic_operation?(node)
260
+ node.respond_to?(:arithmetic_operation?) && node.arithmetic_operation?
261
+ end
262
+
230
263
  def without_argument_parentheses_method?(node)
231
264
  node.send_type? && !node.arguments.empty? &&
232
265
  !node.parenthesized? && !node.operator_method? && !node.assignment_method?
@@ -86,10 +86,6 @@ module RuboCop
86
86
  def indented_else_node(expression, node)
87
87
  "else\n#{indentation(node)}#{expression}"
88
88
  end
89
-
90
- def configured_indentation_width
91
- super || 2
92
- end
93
89
  end
94
90
  end
95
91
  end
@@ -0,0 +1,85 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RuboCop
4
+ module Cop
5
+ module Style
6
+ # Avoid redundant `::` prefix on constant.
7
+ #
8
+ # How Ruby searches constant is a bit complicated, and it can often be difficult to
9
+ # understand from the code whether the `::` is intended or not. Where `Module.nesting`
10
+ # is empty, there is no need to prepend `::`, so it would be nice to consistently
11
+ # avoid such meaningless `::` prefix to avoid confusion.
12
+ #
13
+ # NOTE: This cop is disabled if `Lint/ConstantResolution` cop is enabled to prevent
14
+ # conflicting rules. Because it respects user configurations that want to enable
15
+ # `Lint/ConstantResolution` cop which is disabled by default.
16
+ #
17
+ # @example
18
+ # # bad
19
+ # ::Const
20
+ #
21
+ # # good
22
+ # Const
23
+ #
24
+ # # bad
25
+ # class << self
26
+ # ::Const
27
+ # end
28
+ #
29
+ # # good
30
+ # class << self
31
+ # Const
32
+ # end
33
+ #
34
+ # # good
35
+ # class A
36
+ # ::Const
37
+ # end
38
+ #
39
+ # # good
40
+ # module A
41
+ # ::Const
42
+ # end
43
+ class RedundantConstantBase < Base
44
+ extend AutoCorrector
45
+
46
+ MSG = 'Remove redundant `::`.'
47
+
48
+ def on_cbase(node)
49
+ return if lint_constant_resolution_cop_enabled?
50
+ return unless bad?(node)
51
+
52
+ add_offense(node) do |corrector|
53
+ corrector.remove(node)
54
+ end
55
+ end
56
+
57
+ private
58
+
59
+ def lint_constant_resolution_cop_enabled?
60
+ lint_constant_resolution_config.fetch('Enabled', false)
61
+ end
62
+
63
+ def lint_constant_resolution_config
64
+ config.for_cop('Lint/ConstantResolution')
65
+ end
66
+
67
+ def bad?(node)
68
+ module_nesting_ancestors_of(node).none?
69
+ end
70
+
71
+ def module_nesting_ancestors_of(node)
72
+ node.each_ancestor(:class, :module).reject do |ancestor|
73
+ ancestor.class_type? && used_in_super_class_part?(node, class_node: ancestor)
74
+ end
75
+ end
76
+
77
+ def used_in_super_class_part?(node, class_node:)
78
+ class_node.parent_class&.each_descendant(:cbase)&.any? do |descendant|
79
+ descendant.equal?(node)
80
+ end
81
+ end
82
+ end
83
+ end
84
+ end
85
+ end
@@ -0,0 +1,45 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RuboCop
4
+ module Cop
5
+ module Style
6
+ # Checks for redundant uses of double splat hash braces.
7
+ #
8
+ # @example
9
+ #
10
+ # # bad
11
+ # do_something(**{foo: bar, baz: qux})
12
+ #
13
+ # # good
14
+ # do_something(foo: bar, baz: qux)
15
+ #
16
+ class RedundantDoubleSplatHashBraces < Base
17
+ extend AutoCorrector
18
+
19
+ MSG = 'Remove the redundant double splat and braces, use keyword arguments directly.'
20
+
21
+ def on_hash(node)
22
+ return if node.pairs.empty? || node.pairs.any?(&:hash_rocket?)
23
+ return unless (parent = node.parent)
24
+ return unless parent.kwsplat_type?
25
+
26
+ add_offense(parent) do |corrector|
27
+ corrector.remove(parent.loc.operator)
28
+ corrector.remove(opening_brace(node))
29
+ corrector.remove(closing_brace(node))
30
+ end
31
+ end
32
+
33
+ private
34
+
35
+ def opening_brace(node)
36
+ node.loc.begin.join(node.children.first.source_range.begin)
37
+ end
38
+
39
+ def closing_brace(node)
40
+ node.children.last.source_range.end.join(node.loc.end)
41
+ end
42
+ end
43
+ end
44
+ end
45
+ end
@@ -0,0 +1,116 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RuboCop
4
+ module Cop
5
+ module Style
6
+ # Checks for redundant `each`.
7
+ #
8
+ # @safety
9
+ # This cop is unsafe, as it can produce false positives if the receiver
10
+ # is not an `Enumerator`.
11
+ #
12
+ # @example
13
+ #
14
+ # # bad
15
+ # array.each.each { |v| do_something(v) }
16
+ #
17
+ # # good
18
+ # array.each { |v| do_something(v) }
19
+ #
20
+ # # bad
21
+ # array.each.each_with_index { |v, i| do_something(v, i) }
22
+ #
23
+ # # good
24
+ # array.each.with_index { |v, i| do_something(v, i) }
25
+ # array.each_with_index { |v, i| do_something(v, i) }
26
+ #
27
+ # # bad
28
+ # array.each.each_with_object { |v, o| do_something(v, o) }
29
+ #
30
+ # # good
31
+ # array.each.with_object { |v, o| do_something(v, o) }
32
+ # array.each_with_object { |v, o| do_something(v, o) }
33
+ #
34
+ class RedundantEach < Base
35
+ extend AutoCorrector
36
+
37
+ MSG = 'Remove redundant `each`.'
38
+ MSG_WITH_INDEX = 'Use `with_index` to remove redundant `each`.'
39
+ MSG_WITH_OBJECT = 'Use `with_object` to remove redundant `each`.'
40
+
41
+ RESTRICT_ON_SEND = %i[each each_with_index each_with_object].freeze
42
+
43
+ def on_send(node)
44
+ return unless (redundant_node = redundant_each_method(node))
45
+
46
+ range = range(node)
47
+
48
+ add_offense(range, message: message(node)) do |corrector|
49
+ case node.method_name
50
+ when :each
51
+ remove_redundant_each(corrector, range, redundant_node)
52
+ when :each_with_index
53
+ corrector.replace(node.loc.selector, 'with_index')
54
+ when :each_with_object
55
+ corrector.replace(node.loc.selector, 'with_object')
56
+ end
57
+ end
58
+ end
59
+
60
+ private
61
+
62
+ # rubocop:disable Metrics/AbcSize, Metrics/CyclomaticComplexity, Metrics/PerceivedComplexity
63
+ def redundant_each_method(node)
64
+ return if node.last_argument&.block_pass_type?
65
+
66
+ if node.method?(:each) && !node.parent&.block_type?
67
+ ancestor_node = node.each_ancestor(:send).detect do |ancestor|
68
+ ancestor.receiver == node &&
69
+ (RESTRICT_ON_SEND.include?(ancestor.method_name) || ancestor.method?(:reverse_each))
70
+ end
71
+
72
+ return ancestor_node if ancestor_node
73
+ end
74
+
75
+ return unless (prev_method = node.children.first)
76
+ return if !prev_method.send_type? ||
77
+ prev_method.parent.block_type? || prev_method.last_argument&.block_pass_type?
78
+
79
+ detected = prev_method.method_name.to_s.start_with?('each_') unless node.method?(:each)
80
+
81
+ prev_method if detected || prev_method.method?(:reverse_each)
82
+ end
83
+ # rubocop:enable Metrics/AbcSize, Metrics/CyclomaticComplexity, Metrics/PerceivedComplexity
84
+
85
+ def range(node)
86
+ if node.method?(:each)
87
+ node.loc.dot.join(node.loc.selector)
88
+ else
89
+ node.loc.selector
90
+ end
91
+ end
92
+
93
+ def message(node)
94
+ case node.method_name
95
+ when :each
96
+ MSG
97
+ when :each_with_index
98
+ MSG_WITH_INDEX
99
+ when :each_with_object
100
+ MSG_WITH_OBJECT
101
+ end
102
+ end
103
+
104
+ def remove_redundant_each(corrector, range, redundant_node)
105
+ corrector.remove(range)
106
+
107
+ if redundant_node.method?(:each_with_index)
108
+ corrector.replace(redundant_node.loc.selector, 'each.with_index')
109
+ elsif redundant_node.method?(:each_with_object)
110
+ corrector.replace(redundant_node.loc.selector, 'each.with_object')
111
+ end
112
+ end
113
+ end
114
+ end
115
+ end
116
+ end