rubocop 0.49.1 → 0.52.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.
Files changed (506) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +6 -9
  3. data/bin/rubocop +1 -1
  4. data/config/default.yml +264 -118
  5. data/config/disabled.yml +13 -9
  6. data/config/enabled.yml +1156 -918
  7. data/lib/rubocop.rb +555 -489
  8. data/lib/rubocop/ast/builder.rb +6 -1
  9. data/lib/rubocop/ast/node.rb +68 -52
  10. data/lib/rubocop/ast/node/args_node.rb +15 -10
  11. data/lib/rubocop/ast/node/array_node.rb +10 -1
  12. data/lib/rubocop/ast/node/block_node.rb +9 -0
  13. data/lib/rubocop/ast/node/def_node.rb +71 -0
  14. data/lib/rubocop/ast/node/for_node.rb +8 -0
  15. data/lib/rubocop/ast/node/if_node.rb +10 -2
  16. data/lib/rubocop/ast/node/mixin/basic_literal_node.rb +16 -0
  17. data/lib/rubocop/ast/node/mixin/collection_node.rb +15 -0
  18. data/lib/rubocop/ast/node/mixin/method_dispatch_node.rb +174 -0
  19. data/lib/rubocop/ast/node/mixin/method_identifier_predicates.rb +89 -0
  20. data/lib/rubocop/ast/node/mixin/parameterized_node.rb +18 -31
  21. data/lib/rubocop/ast/node/regexp_node.rb +35 -0
  22. data/lib/rubocop/ast/node/send_node.rb +21 -150
  23. data/lib/rubocop/ast/node/str_node.rb +14 -0
  24. data/lib/rubocop/ast/node/super_node.rb +3 -24
  25. data/lib/rubocop/ast/node/symbol_node.rb +20 -0
  26. data/lib/rubocop/ast/node/yield_node.rb +21 -0
  27. data/lib/rubocop/ast/traversal.rb +7 -7
  28. data/lib/rubocop/cached_data.rb +1 -6
  29. data/lib/rubocop/cli.rb +59 -13
  30. data/lib/rubocop/comment_config.rb +2 -5
  31. data/lib/rubocop/config.rb +136 -29
  32. data/lib/rubocop/config_loader.rb +61 -104
  33. data/lib/rubocop/config_loader_resolver.rb +102 -4
  34. data/lib/rubocop/cop/autocorrect_logic.rb +1 -1
  35. data/lib/rubocop/cop/bundler/duplicated_gem.rb +13 -11
  36. data/lib/rubocop/cop/bundler/insecure_protocol_source.rb +67 -0
  37. data/lib/rubocop/cop/bundler/ordered_gems.rb +7 -58
  38. data/lib/rubocop/cop/commissioner.rb +6 -3
  39. data/lib/rubocop/cop/cop.rb +11 -6
  40. data/lib/rubocop/cop/gemspec/duplicated_assignment.rb +102 -0
  41. data/lib/rubocop/cop/gemspec/ordered_dependencies.rb +97 -0
  42. data/lib/rubocop/cop/gemspec/required_ruby_version.rb +87 -0
  43. data/lib/rubocop/cop/generator.rb +122 -25
  44. data/lib/rubocop/cop/internal_affairs.rb +6 -2
  45. data/lib/rubocop/cop/internal_affairs/node_destructuring.rb +46 -0
  46. data/lib/rubocop/cop/internal_affairs/node_type_predicate.rb +16 -5
  47. data/lib/rubocop/cop/internal_affairs/offense_location_keyword.rb +54 -0
  48. data/lib/rubocop/cop/internal_affairs/redundant_location_argument.rb +59 -0
  49. data/lib/rubocop/cop/internal_affairs/redundant_message_argument.rb +71 -0
  50. data/lib/rubocop/cop/internal_affairs/useless_message_assertion.rb +3 -3
  51. data/lib/rubocop/cop/layout/access_modifier_indentation.rb +6 -10
  52. data/lib/rubocop/cop/layout/align_array.rb +2 -2
  53. data/lib/rubocop/cop/layout/align_hash.rb +18 -18
  54. data/lib/rubocop/cop/layout/align_parameters.rb +11 -23
  55. data/lib/rubocop/cop/layout/block_end_newline.rb +20 -6
  56. data/lib/rubocop/cop/layout/case_indentation.rb +15 -18
  57. data/lib/rubocop/cop/layout/class_structure.rb +306 -0
  58. data/lib/rubocop/cop/layout/closing_parenthesis_indentation.rb +7 -6
  59. data/lib/rubocop/cop/layout/comment_indentation.rb +42 -3
  60. data/lib/rubocop/cop/layout/dot_position.rb +31 -13
  61. data/lib/rubocop/cop/layout/else_alignment.rb +37 -17
  62. data/lib/rubocop/cop/layout/empty_line_after_magic_comment.rb +1 -1
  63. data/lib/rubocop/cop/layout/empty_line_between_defs.rb +22 -18
  64. data/lib/rubocop/cop/layout/empty_lines.rb +16 -2
  65. data/lib/rubocop/cop/layout/empty_lines_around_access_modifier.rb +23 -6
  66. data/lib/rubocop/cop/layout/empty_lines_around_arguments.rb +89 -0
  67. data/lib/rubocop/cop/layout/empty_lines_around_begin_body.rb +2 -2
  68. data/lib/rubocop/cop/layout/empty_lines_around_block_body.rb +4 -8
  69. data/lib/rubocop/cop/layout/empty_lines_around_class_body.rb +30 -5
  70. data/lib/rubocop/cop/layout/empty_lines_around_exception_handling_keywords.rb +10 -6
  71. data/lib/rubocop/cop/layout/empty_lines_around_method_body.rb +5 -5
  72. data/lib/rubocop/cop/layout/empty_lines_around_module_body.rb +22 -7
  73. data/lib/rubocop/cop/layout/end_of_line.rb +2 -2
  74. data/lib/rubocop/cop/layout/extra_spacing.rb +23 -26
  75. data/lib/rubocop/cop/layout/first_method_parameter_line_break.rb +3 -3
  76. data/lib/rubocop/cop/layout/first_parameter_indentation.rb +9 -3
  77. data/lib/rubocop/cop/layout/indent_array.rb +68 -21
  78. data/lib/rubocop/cop/layout/indent_hash.rb +71 -26
  79. data/lib/rubocop/cop/layout/indent_heredoc.rb +70 -35
  80. data/lib/rubocop/cop/layout/indentation_consistency.rb +1 -2
  81. data/lib/rubocop/cop/layout/indentation_width.rb +40 -27
  82. data/lib/rubocop/cop/layout/initial_indentation.rb +10 -7
  83. data/lib/rubocop/cop/layout/leading_comment_space.rb +32 -17
  84. data/lib/rubocop/cop/layout/multiline_array_brace_layout.rb +47 -14
  85. data/lib/rubocop/cop/layout/multiline_assignment_layout.rb +12 -11
  86. data/lib/rubocop/cop/layout/multiline_block_layout.rb +19 -16
  87. data/lib/rubocop/cop/layout/multiline_hash_brace_layout.rb +46 -13
  88. data/lib/rubocop/cop/layout/multiline_method_call_indentation.rb +29 -27
  89. data/lib/rubocop/cop/layout/multiline_method_definition_brace_layout.rb +7 -3
  90. data/lib/rubocop/cop/layout/multiline_operation_indentation.rb +6 -0
  91. data/lib/rubocop/cop/layout/rescue_ensure_alignment.rb +12 -4
  92. data/lib/rubocop/cop/layout/space_after_colon.rb +13 -6
  93. data/lib/rubocop/cop/layout/space_after_comma.rb +11 -1
  94. data/lib/rubocop/cop/layout/space_after_method_name.rb +8 -6
  95. data/lib/rubocop/cop/layout/space_after_not.rb +1 -1
  96. data/lib/rubocop/cop/layout/space_after_semicolon.rb +8 -1
  97. data/lib/rubocop/cop/layout/space_around_block_parameters.rb +32 -25
  98. data/lib/rubocop/cop/layout/space_around_equals_in_parameter_default.rb +28 -17
  99. data/lib/rubocop/cop/layout/space_around_keyword.rb +22 -16
  100. data/lib/rubocop/cop/layout/space_around_operators.rb +27 -14
  101. data/lib/rubocop/cop/layout/space_before_block_braces.rb +61 -12
  102. data/lib/rubocop/cop/layout/space_before_comma.rb +12 -1
  103. data/lib/rubocop/cop/layout/space_before_comment.rb +10 -5
  104. data/lib/rubocop/cop/layout/space_before_first_arg.rb +5 -4
  105. data/lib/rubocop/cop/layout/space_before_semicolon.rb +8 -1
  106. data/lib/rubocop/cop/layout/space_in_lambda_literal.rb +12 -14
  107. data/lib/rubocop/cop/layout/space_inside_array_literal_brackets.rb +235 -0
  108. data/lib/rubocop/cop/layout/space_inside_array_percent_literal.rb +4 -4
  109. data/lib/rubocop/cop/layout/space_inside_block_braces.rb +89 -18
  110. data/lib/rubocop/cop/layout/space_inside_hash_literal_braces.rb +62 -36
  111. data/lib/rubocop/cop/layout/space_inside_parens.rb +40 -3
  112. data/lib/rubocop/cop/layout/space_inside_percent_literal_delimiters.rb +1 -1
  113. data/lib/rubocop/cop/layout/space_inside_range_literal.rb +15 -15
  114. data/lib/rubocop/cop/layout/space_inside_reference_brackets.rb +81 -0
  115. data/lib/rubocop/cop/layout/space_inside_string_interpolation.rb +32 -17
  116. data/lib/rubocop/cop/layout/tab.rb +7 -4
  117. data/lib/rubocop/cop/layout/trailing_blank_lines.rb +11 -9
  118. data/lib/rubocop/cop/layout/trailing_whitespace.rb +1 -1
  119. data/lib/rubocop/cop/lint/ambiguous_block_association.rb +12 -19
  120. data/lib/rubocop/cop/lint/assignment_in_condition.rb +16 -2
  121. data/lib/rubocop/cop/lint/block_alignment.rb +42 -30
  122. data/lib/rubocop/cop/lint/boolean_symbol.rb +38 -0
  123. data/lib/rubocop/cop/lint/circular_argument_reference.rb +3 -14
  124. data/lib/rubocop/cop/lint/condition_position.rb +5 -1
  125. data/lib/rubocop/cop/lint/debugger.rb +18 -11
  126. data/lib/rubocop/cop/lint/def_end_alignment.rb +9 -14
  127. data/lib/rubocop/cop/lint/deprecated_class_methods.rb +4 -4
  128. data/lib/rubocop/cop/lint/duplicate_case_condition.rb +3 -3
  129. data/lib/rubocop/cop/lint/duplicate_methods.rb +75 -5
  130. data/lib/rubocop/cop/lint/duplicated_key.rb +1 -1
  131. data/lib/rubocop/cop/lint/each_with_object_argument.rb +1 -1
  132. data/lib/rubocop/cop/lint/else_layout.rb +3 -3
  133. data/lib/rubocop/cop/lint/empty_ensure.rb +1 -1
  134. data/lib/rubocop/cop/lint/empty_expression.rb +1 -1
  135. data/lib/rubocop/cop/lint/empty_interpolation.rb +1 -1
  136. data/lib/rubocop/cop/lint/empty_when.rb +1 -1
  137. data/lib/rubocop/cop/lint/end_alignment.rb +13 -14
  138. data/lib/rubocop/cop/lint/end_in_method.rb +1 -1
  139. data/lib/rubocop/cop/lint/ensure_return.rb +1 -1
  140. data/lib/rubocop/cop/lint/float_out_of_range.rb +5 -5
  141. data/lib/rubocop/cop/lint/format_parameter_mismatch.rb +36 -41
  142. data/lib/rubocop/cop/lint/handle_exceptions.rb +1 -1
  143. data/lib/rubocop/cop/lint/implicit_string_concatenation.rb +1 -1
  144. data/lib/rubocop/cop/lint/ineffective_access_modifier.rb +25 -20
  145. data/lib/rubocop/cop/lint/inherit_exception.rb +16 -19
  146. data/lib/rubocop/cop/lint/interpolation_check.rb +37 -0
  147. data/lib/rubocop/cop/lint/{literal_in_condition.rb → literal_as_condition.rb} +21 -7
  148. data/lib/rubocop/cop/lint/literal_in_interpolation.rb +1 -1
  149. data/lib/rubocop/cop/lint/loop.rb +1 -1
  150. data/lib/rubocop/cop/lint/missing_cop_enable_directive.rb +81 -0
  151. data/lib/rubocop/cop/lint/multiple_compare.rb +1 -1
  152. data/lib/rubocop/cop/lint/nested_method_definition.rb +6 -8
  153. data/lib/rubocop/cop/lint/nested_percent_literal.rb +58 -0
  154. data/lib/rubocop/cop/lint/next_without_accumulator.rb +1 -1
  155. data/lib/rubocop/cop/lint/non_local_exit_from_iterator.rb +4 -4
  156. data/lib/rubocop/cop/lint/parentheses_as_grouped_expression.rb +4 -3
  157. data/lib/rubocop/cop/lint/percent_string_array.rb +13 -22
  158. data/lib/rubocop/cop/lint/percent_symbol_array.rb +12 -12
  159. data/lib/rubocop/cop/lint/rand_one.rb +8 -2
  160. data/lib/rubocop/cop/lint/redundant_with_index.rb +80 -0
  161. data/lib/rubocop/cop/lint/redundant_with_object.rb +81 -0
  162. data/lib/rubocop/cop/lint/regexp_as_condition.rb +29 -0
  163. data/lib/rubocop/cop/lint/require_parentheses.rb +5 -3
  164. data/lib/rubocop/cop/lint/rescue_exception.rb +1 -1
  165. data/lib/rubocop/cop/lint/rescue_type.rb +18 -9
  166. data/lib/rubocop/cop/lint/return_in_void_context.rb +74 -0
  167. data/lib/rubocop/cop/lint/safe_navigation_chain.rb +1 -1
  168. data/lib/rubocop/cop/lint/script_permission.rb +8 -1
  169. data/lib/rubocop/cop/lint/shadowed_argument.rb +146 -0
  170. data/lib/rubocop/cop/lint/shadowed_exception.rb +37 -10
  171. data/lib/rubocop/cop/lint/shadowing_outer_local_variable.rb +1 -1
  172. data/lib/rubocop/cop/lint/string_conversion_in_interpolation.rb +7 -7
  173. data/lib/rubocop/cop/lint/syntax.rb +23 -20
  174. data/lib/rubocop/cop/lint/underscore_prefixed_variable_name.rb +1 -1
  175. data/lib/rubocop/cop/lint/unified_integer.rb +5 -4
  176. data/lib/rubocop/cop/lint/unneeded_disable.rb +41 -16
  177. data/lib/rubocop/cop/lint/unneeded_require_statement.rb +51 -0
  178. data/lib/rubocop/cop/lint/unneeded_splat_expansion.rb +45 -19
  179. data/lib/rubocop/cop/lint/unreachable_code.rb +53 -8
  180. data/lib/rubocop/cop/lint/unused_method_argument.rb +2 -1
  181. data/lib/rubocop/cop/lint/uri_escape_unescape.rb +74 -0
  182. data/lib/rubocop/cop/lint/uri_regexp.rb +73 -0
  183. data/lib/rubocop/cop/lint/useless_access_modifier.rb +12 -16
  184. data/lib/rubocop/cop/lint/useless_assignment.rb +1 -1
  185. data/lib/rubocop/cop/lint/useless_comparison.rb +1 -1
  186. data/lib/rubocop/cop/lint/useless_setter_call.rb +15 -12
  187. data/lib/rubocop/cop/lint/void.rb +38 -27
  188. data/lib/rubocop/cop/message_annotator.rb +4 -2
  189. data/lib/rubocop/cop/metrics/abc_size.rb +2 -2
  190. data/lib/rubocop/cop/metrics/block_nesting.rb +1 -1
  191. data/lib/rubocop/cop/metrics/class_length.rb +3 -1
  192. data/lib/rubocop/cop/metrics/cyclomatic_complexity.rb +2 -1
  193. data/lib/rubocop/cop/metrics/line_length.rb +8 -5
  194. data/lib/rubocop/cop/metrics/method_length.rb +8 -3
  195. data/lib/rubocop/cop/metrics/module_length.rb +3 -1
  196. data/lib/rubocop/cop/metrics/parameter_lists.rb +14 -5
  197. data/lib/rubocop/cop/metrics/perceived_complexity.rb +2 -1
  198. data/lib/rubocop/cop/mixin/array_hash_indentation.rb +3 -2
  199. data/lib/rubocop/cop/mixin/autocorrect_alignment.rb +2 -2
  200. data/lib/rubocop/cop/mixin/code_length.rb +1 -1
  201. data/lib/rubocop/cop/mixin/configurable_formatting.rb +1 -1
  202. data/lib/rubocop/cop/mixin/def_node.rb +1 -1
  203. data/lib/rubocop/cop/mixin/documentation_comment.rb +1 -1
  204. data/lib/rubocop/cop/mixin/empty_lines_around_body.rb +14 -7
  205. data/lib/rubocop/cop/mixin/empty_parameter.rb +23 -0
  206. data/lib/rubocop/cop/mixin/end_keyword_alignment.rb +8 -4
  207. data/lib/rubocop/cop/mixin/enforce_superclass.rb +3 -3
  208. data/lib/rubocop/cop/mixin/first_element_line_break.rb +12 -3
  209. data/lib/rubocop/cop/mixin/heredoc.rb +28 -0
  210. data/lib/rubocop/cop/mixin/method_complexity.rb +33 -7
  211. data/lib/rubocop/cop/mixin/multiline_expression_indentation.rb +74 -33
  212. data/lib/rubocop/cop/mixin/multiline_literal_brace_layout.rb +34 -8
  213. data/lib/rubocop/cop/mixin/negative_conditional.rb +4 -1
  214. data/lib/rubocop/cop/mixin/ordered_gem_node.rb +67 -0
  215. data/lib/rubocop/cop/mixin/parentheses.rb +12 -0
  216. data/lib/rubocop/cop/mixin/parser_diagnostic.rb +4 -1
  217. data/lib/rubocop/cop/mixin/percent_array.rb +52 -0
  218. data/lib/rubocop/cop/mixin/space_after_punctuation.rb +9 -8
  219. data/lib/rubocop/cop/mixin/space_before_punctuation.rb +11 -10
  220. data/lib/rubocop/cop/mixin/statement_modifier.rb +7 -17
  221. data/lib/rubocop/cop/mixin/string_help.rb +1 -1
  222. data/lib/rubocop/cop/mixin/string_literals_help.rb +1 -1
  223. data/lib/rubocop/cop/mixin/surrounding_space.rb +95 -8
  224. data/lib/rubocop/cop/mixin/too_many_lines.rb +2 -2
  225. data/lib/rubocop/cop/mixin/trailing_comma.rb +25 -17
  226. data/lib/rubocop/cop/mixin/unused_argument.rb +6 -2
  227. data/lib/rubocop/cop/naming/accessor_method_name.rb +55 -0
  228. data/lib/rubocop/cop/{style → naming}/ascii_identifiers.rb +35 -2
  229. data/lib/rubocop/cop/{style/op_method.rb → naming/binary_operator_parameter_name.rb} +7 -6
  230. data/lib/rubocop/cop/naming/class_and_module_camel_case.rb +33 -0
  231. data/lib/rubocop/cop/naming/constant_name.rb +58 -0
  232. data/lib/rubocop/cop/{style → naming}/file_name.rb +28 -13
  233. data/lib/rubocop/cop/naming/heredoc_delimiter_case.rb +62 -0
  234. data/lib/rubocop/cop/naming/heredoc_delimiter_naming.rb +59 -0
  235. data/lib/rubocop/cop/naming/method_name.rb +40 -0
  236. data/lib/rubocop/cop/naming/predicate_name.rb +101 -0
  237. data/lib/rubocop/cop/naming/variable_name.rb +50 -0
  238. data/lib/rubocop/cop/{style → naming}/variable_number.rb +11 -28
  239. data/lib/rubocop/cop/offense.rb +6 -1
  240. data/lib/rubocop/cop/performance/caller.rb +39 -11
  241. data/lib/rubocop/cop/performance/case_when_splat.rb +3 -7
  242. data/lib/rubocop/cop/performance/casecmp.rb +9 -8
  243. data/lib/rubocop/cop/performance/compare_with_block.rb +23 -13
  244. data/lib/rubocop/cop/performance/count.rb +7 -4
  245. data/lib/rubocop/cop/performance/detect.rb +9 -6
  246. data/lib/rubocop/cop/performance/double_start_end_with.rb +12 -20
  247. data/lib/rubocop/cop/performance/end_with.rb +6 -6
  248. data/lib/rubocop/cop/performance/fixed_size.rb +1 -1
  249. data/lib/rubocop/cop/performance/flat_map.rb +5 -2
  250. data/lib/rubocop/cop/performance/hash_each_methods.rb +85 -40
  251. data/lib/rubocop/cop/performance/lstrip_rstrip.rb +9 -6
  252. data/lib/rubocop/cop/performance/range_include.rb +3 -3
  253. data/lib/rubocop/cop/performance/redundant_block_call.rb +28 -28
  254. data/lib/rubocop/cop/performance/redundant_match.rb +13 -12
  255. data/lib/rubocop/cop/performance/redundant_merge.rb +44 -26
  256. data/lib/rubocop/cop/performance/redundant_sort_by.rb +9 -6
  257. data/lib/rubocop/cop/performance/regexp_match.rb +19 -10
  258. data/lib/rubocop/cop/performance/reverse_each.rb +1 -1
  259. data/lib/rubocop/cop/performance/sample.rb +1 -1
  260. data/lib/rubocop/cop/performance/size.rb +3 -3
  261. data/lib/rubocop/cop/performance/start_with.rb +6 -6
  262. data/lib/rubocop/cop/performance/string_replacement.rb +6 -6
  263. data/lib/rubocop/cop/performance/times_map.rb +32 -22
  264. data/lib/rubocop/cop/performance/unfreeze_string.rb +50 -0
  265. data/lib/rubocop/cop/performance/uri_default_parser.rb +47 -0
  266. data/lib/rubocop/cop/rails/action_filter.rb +23 -1
  267. data/lib/rubocop/cop/rails/active_support_aliases.rb +4 -5
  268. data/lib/rubocop/cop/rails/application_job.rb +5 -3
  269. data/lib/rubocop/cop/rails/application_record.rb +5 -3
  270. data/lib/rubocop/cop/rails/blank.rb +20 -17
  271. data/lib/rubocop/cop/rails/create_table_with_timestamps.rb +82 -0
  272. data/lib/rubocop/cop/rails/date.rb +7 -6
  273. data/lib/rubocop/cop/rails/delegate.rb +53 -29
  274. data/lib/rubocop/cop/rails/delegate_allow_blank.rb +4 -4
  275. data/lib/rubocop/cop/rails/dynamic_find_by.rb +2 -2
  276. data/lib/rubocop/cop/rails/enum_uniqueness.rb +4 -4
  277. data/lib/rubocop/cop/rails/environment_comparison.rb +66 -0
  278. data/lib/rubocop/cop/rails/exit.rb +8 -1
  279. data/lib/rubocop/cop/rails/file_path.rb +8 -11
  280. data/lib/rubocop/cop/rails/find_by.rb +2 -1
  281. data/lib/rubocop/cop/rails/find_each.rb +1 -1
  282. data/lib/rubocop/cop/rails/has_and_belongs_to_many.rb +8 -1
  283. data/lib/rubocop/cop/rails/has_many_or_has_one_dependent.rb +76 -0
  284. data/lib/rubocop/cop/rails/http_positional_arguments.rb +40 -44
  285. data/lib/rubocop/cop/rails/inverse_of.rb +96 -0
  286. data/lib/rubocop/cop/rails/lexically_scoped_action_filter.rb +112 -0
  287. data/lib/rubocop/cop/rails/not_null_column.rb +6 -6
  288. data/lib/rubocop/cop/rails/output.rb +11 -2
  289. data/lib/rubocop/cop/rails/output_safety.rb +16 -21
  290. data/lib/rubocop/cop/rails/pluralization_grammar.rb +10 -10
  291. data/lib/rubocop/cop/rails/presence.rb +105 -0
  292. data/lib/rubocop/cop/rails/present.rb +14 -17
  293. data/lib/rubocop/cop/rails/read_write_attribute.rb +13 -13
  294. data/lib/rubocop/cop/rails/redundant_receiver_in_with_options.rb +91 -0
  295. data/lib/rubocop/cop/rails/relative_date_constant.rb +11 -11
  296. data/lib/rubocop/cop/rails/request_referer.rb +3 -3
  297. data/lib/rubocop/cop/rails/reversible_migration.rb +36 -35
  298. data/lib/rubocop/cop/rails/safe_navigation.rb +7 -8
  299. data/lib/rubocop/cop/rails/save_bang.rb +19 -17
  300. data/lib/rubocop/cop/rails/scope_args.rb +2 -2
  301. data/lib/rubocop/cop/rails/skips_model_validations.rb +2 -2
  302. data/lib/rubocop/cop/rails/time_zone.rb +3 -2
  303. data/lib/rubocop/cop/rails/uniq_before_pluck.rb +4 -2
  304. data/lib/rubocop/cop/rails/unknown_env.rb +63 -0
  305. data/lib/rubocop/cop/rails/validation.rb +8 -8
  306. data/lib/rubocop/cop/registry.rb +2 -1
  307. data/lib/rubocop/cop/security/eval.rb +4 -4
  308. data/lib/rubocop/cop/security/json_load.rb +7 -5
  309. data/lib/rubocop/cop/security/marshal_load.rb +8 -6
  310. data/lib/rubocop/cop/security/yaml_load.rb +4 -4
  311. data/lib/rubocop/cop/style/alias.rb +49 -27
  312. data/lib/rubocop/cop/style/and_or.rb +65 -45
  313. data/lib/rubocop/cop/style/array_join.rb +10 -1
  314. data/lib/rubocop/cop/style/ascii_comments.rb +24 -4
  315. data/lib/rubocop/cop/style/attr.rb +15 -5
  316. data/lib/rubocop/cop/style/auto_resource_cleanup.rb +7 -5
  317. data/lib/rubocop/cop/style/bare_percent_literals.rb +31 -10
  318. data/lib/rubocop/cop/style/begin_block.rb +1 -1
  319. data/lib/rubocop/cop/style/block_comments.rb +17 -3
  320. data/lib/rubocop/cop/style/block_delimiters.rb +82 -16
  321. data/lib/rubocop/cop/style/braces_around_hash_parameters.rb +68 -32
  322. data/lib/rubocop/cop/style/case_equality.rb +13 -1
  323. data/lib/rubocop/cop/style/character_literal.rb +10 -0
  324. data/lib/rubocop/cop/style/class_and_module_children.rb +8 -4
  325. data/lib/rubocop/cop/style/class_check.rb +29 -10
  326. data/lib/rubocop/cop/style/class_methods.rb +10 -9
  327. data/lib/rubocop/cop/style/class_vars.rb +5 -4
  328. data/lib/rubocop/cop/style/collection_methods.rb +5 -3
  329. data/lib/rubocop/cop/style/colon_method_call.rb +18 -2
  330. data/lib/rubocop/cop/style/colon_method_definition.rb +36 -0
  331. data/lib/rubocop/cop/style/command_literal.rb +90 -30
  332. data/lib/rubocop/cop/style/comment_annotation.rb +39 -11
  333. data/lib/rubocop/cop/style/commented_keyword.rb +84 -0
  334. data/lib/rubocop/cop/style/conditional_assignment.rb +41 -41
  335. data/lib/rubocop/cop/style/copyright.rb +27 -28
  336. data/lib/rubocop/cop/style/date_time.rb +44 -0
  337. data/lib/rubocop/cop/style/def_with_parentheses.rb +31 -5
  338. data/lib/rubocop/cop/style/dir.rb +48 -0
  339. data/lib/rubocop/cop/style/documentation.rb +17 -2
  340. data/lib/rubocop/cop/style/documentation_method.rb +2 -6
  341. data/lib/rubocop/cop/style/double_negation.rb +1 -1
  342. data/lib/rubocop/cop/style/each_for_simple_loop.rb +8 -8
  343. data/lib/rubocop/cop/style/each_with_object.rb +6 -5
  344. data/lib/rubocop/cop/style/empty_block_parameter.rb +47 -0
  345. data/lib/rubocop/cop/style/empty_case_condition.rb +3 -3
  346. data/lib/rubocop/cop/style/empty_else.rb +55 -24
  347. data/lib/rubocop/cop/style/empty_lambda_parameter.rb +43 -0
  348. data/lib/rubocop/cop/style/empty_literal.rb +25 -14
  349. data/lib/rubocop/cop/style/empty_method.rb +29 -25
  350. data/lib/rubocop/cop/style/encoding.rb +8 -51
  351. data/lib/rubocop/cop/style/end_block.rb +1 -1
  352. data/lib/rubocop/cop/style/eval_with_location.rb +146 -0
  353. data/lib/rubocop/cop/style/even_odd.rb +4 -2
  354. data/lib/rubocop/cop/style/extend_self.rb +92 -0
  355. data/lib/rubocop/cop/style/flip_flop.rb +13 -2
  356. data/lib/rubocop/cop/style/for.rb +6 -2
  357. data/lib/rubocop/cop/style/format_string.rb +33 -5
  358. data/lib/rubocop/cop/style/format_string_token.rb +17 -15
  359. data/lib/rubocop/cop/style/frozen_string_literal_comment.rb +7 -6
  360. data/lib/rubocop/cop/style/global_vars.rb +12 -2
  361. data/lib/rubocop/cop/style/guard_clause.rb +6 -4
  362. data/lib/rubocop/cop/style/hash_syntax.rb +56 -56
  363. data/lib/rubocop/cop/style/identical_conditional_branches.rb +12 -8
  364. data/lib/rubocop/cop/style/if_inside_else.rb +11 -11
  365. data/lib/rubocop/cop/style/if_unless_modifier.rb +8 -7
  366. data/lib/rubocop/cop/style/if_unless_modifier_of_if_unless.rb +3 -2
  367. data/lib/rubocop/cop/style/if_with_semicolon.rb +10 -1
  368. data/lib/rubocop/cop/style/implicit_runtime_error.rb +7 -6
  369. data/lib/rubocop/cop/style/infinite_loop.rb +4 -4
  370. data/lib/rubocop/cop/style/inline_comment.rb +1 -1
  371. data/lib/rubocop/cop/style/inverse_methods.rb +24 -14
  372. data/lib/rubocop/cop/style/lambda.rb +45 -43
  373. data/lib/rubocop/cop/style/lambda_call.rb +37 -10
  374. data/lib/rubocop/cop/style/line_end_concatenation.rb +5 -5
  375. data/lib/rubocop/cop/style/method_call_with_args_parentheses.rb +3 -19
  376. data/lib/rubocop/cop/style/method_call_without_args_parentheses.rb +6 -4
  377. data/lib/rubocop/cop/style/method_called_on_do_end_block.rb +1 -1
  378. data/lib/rubocop/cop/style/method_def_parentheses.rb +20 -25
  379. data/lib/rubocop/cop/style/method_missing.rb +13 -26
  380. data/lib/rubocop/cop/style/min_max.rb +68 -0
  381. data/lib/rubocop/cop/style/missing_else.rb +20 -6
  382. data/lib/rubocop/cop/style/mixin_grouping.rb +31 -21
  383. data/lib/rubocop/cop/style/mixin_usage.rb +71 -0
  384. data/lib/rubocop/cop/style/module_function.rb +27 -11
  385. data/lib/rubocop/cop/style/multiline_block_chain.rb +1 -1
  386. data/lib/rubocop/cop/style/multiline_if_modifier.rb +8 -4
  387. data/lib/rubocop/cop/style/multiline_if_then.rb +15 -13
  388. data/lib/rubocop/cop/style/multiline_memoization.rb +33 -17
  389. data/lib/rubocop/cop/style/multiline_ternary_operator.rb +1 -1
  390. data/lib/rubocop/cop/style/multiple_comparison.rb +1 -1
  391. data/lib/rubocop/cop/style/mutable_constant.rb +11 -15
  392. data/lib/rubocop/cop/style/negated_if.rb +27 -31
  393. data/lib/rubocop/cop/style/negated_while.rb +1 -5
  394. data/lib/rubocop/cop/style/nested_modifier.rb +1 -1
  395. data/lib/rubocop/cop/style/nested_parenthesized_calls.rb +26 -23
  396. data/lib/rubocop/cop/style/nested_ternary_operator.rb +1 -1
  397. data/lib/rubocop/cop/style/next.rb +41 -12
  398. data/lib/rubocop/cop/style/nil_comparison.rb +8 -8
  399. data/lib/rubocop/cop/style/non_nil_check.rb +41 -38
  400. data/lib/rubocop/cop/style/not.rb +15 -5
  401. data/lib/rubocop/cop/style/numeric_literal_prefix.rb +8 -4
  402. data/lib/rubocop/cop/style/numeric_literals.rb +9 -9
  403. data/lib/rubocop/cop/style/numeric_predicate.rb +21 -21
  404. data/lib/rubocop/cop/style/one_line_conditional.rb +9 -4
  405. data/lib/rubocop/cop/style/option_hash.rb +11 -25
  406. data/lib/rubocop/cop/style/optional_arguments.rb +1 -2
  407. data/lib/rubocop/cop/style/or_assignment.rb +88 -0
  408. data/lib/rubocop/cop/style/parallel_assignment.rb +16 -16
  409. data/lib/rubocop/cop/style/parentheses_around_condition.rb +30 -13
  410. data/lib/rubocop/cop/style/percent_literal_delimiters.rb +25 -4
  411. data/lib/rubocop/cop/style/percent_q_literals.rb +29 -8
  412. data/lib/rubocop/cop/style/perl_backrefs.rb +8 -1
  413. data/lib/rubocop/cop/style/preferred_hash_methods.rb +7 -11
  414. data/lib/rubocop/cop/style/proc.rb +10 -2
  415. data/lib/rubocop/cop/style/raise_args.rb +22 -29
  416. data/lib/rubocop/cop/style/random_with_offset.rb +160 -0
  417. data/lib/rubocop/cop/style/redundant_begin.rb +16 -5
  418. data/lib/rubocop/cop/style/redundant_conditional.rb +96 -0
  419. data/lib/rubocop/cop/style/redundant_exception.rb +4 -4
  420. data/lib/rubocop/cop/style/redundant_freeze.rb +1 -1
  421. data/lib/rubocop/cop/style/redundant_parentheses.rb +14 -12
  422. data/lib/rubocop/cop/style/redundant_return.rb +28 -15
  423. data/lib/rubocop/cop/style/redundant_self.rb +35 -27
  424. data/lib/rubocop/cop/style/regexp_literal.rb +88 -27
  425. data/lib/rubocop/cop/style/rescue_modifier.rb +12 -1
  426. data/lib/rubocop/cop/style/rescue_standard_error.rb +122 -0
  427. data/lib/rubocop/cop/style/return_nil.rb +89 -0
  428. data/lib/rubocop/cop/style/safe_navigation.rb +100 -48
  429. data/lib/rubocop/cop/style/self_assignment.rb +13 -13
  430. data/lib/rubocop/cop/style/semicolon.rb +19 -9
  431. data/lib/rubocop/cop/style/send.rb +10 -1
  432. data/lib/rubocop/cop/style/signal_exception.rb +104 -3
  433. data/lib/rubocop/cop/style/single_line_block_params.rb +16 -15
  434. data/lib/rubocop/cop/style/single_line_methods.rb +26 -18
  435. data/lib/rubocop/cop/style/special_global_vars.rb +19 -14
  436. data/lib/rubocop/cop/style/stabby_lambda_parentheses.rb +23 -50
  437. data/lib/rubocop/cop/style/stderr_puts.rb +54 -0
  438. data/lib/rubocop/cop/style/string_hash_keys.rb +36 -0
  439. data/lib/rubocop/cop/style/string_literals.rb +26 -3
  440. data/lib/rubocop/cop/style/string_literals_in_interpolation.rb +16 -1
  441. data/lib/rubocop/cop/style/string_methods.rb +19 -8
  442. data/lib/rubocop/cop/style/struct_inheritance.rb +3 -3
  443. data/lib/rubocop/cop/style/symbol_array.rb +7 -35
  444. data/lib/rubocop/cop/style/symbol_literal.rb +1 -1
  445. data/lib/rubocop/cop/style/symbol_proc.rb +11 -25
  446. data/lib/rubocop/cop/style/ternary_parentheses.rb +46 -51
  447. data/lib/rubocop/cop/style/trailing_body_on_method_definition.rb +101 -0
  448. data/lib/rubocop/cop/style/trailing_comma_in_arguments.rb +20 -6
  449. data/lib/rubocop/cop/style/trailing_comma_in_literal.rb +22 -7
  450. data/lib/rubocop/cop/style/trailing_method_end_statement.rb +95 -0
  451. data/lib/rubocop/cop/style/trailing_underscore_variable.rb +70 -24
  452. data/lib/rubocop/cop/style/trivial_accessors.rb +72 -65
  453. data/lib/rubocop/cop/style/unless_else.rb +16 -1
  454. data/lib/rubocop/cop/style/unneeded_capital_w.rb +18 -8
  455. data/lib/rubocop/cop/style/unneeded_interpolation.rb +15 -19
  456. data/lib/rubocop/cop/style/unneeded_percent_q.rb +14 -13
  457. data/lib/rubocop/cop/style/variable_interpolation.rb +23 -9
  458. data/lib/rubocop/cop/style/when_then.rb +14 -1
  459. data/lib/rubocop/cop/style/while_until_do.rb +27 -4
  460. data/lib/rubocop/cop/style/while_until_modifier.rb +26 -6
  461. data/lib/rubocop/cop/style/word_array.rb +9 -30
  462. data/lib/rubocop/cop/style/yoda_condition.rb +51 -22
  463. data/lib/rubocop/cop/style/zero_length_predicate.rb +44 -29
  464. data/lib/rubocop/cop/team.rb +16 -8
  465. data/lib/rubocop/cop/util.rb +43 -34
  466. data/lib/rubocop/cop/variable_force.rb +1 -1
  467. data/lib/rubocop/cop/variable_force/assignment.rb +4 -2
  468. data/lib/rubocop/cop/variable_force/scope.rb +1 -5
  469. data/lib/rubocop/cop/variable_force/variable.rb +1 -1
  470. data/lib/rubocop/formatter/disabled_config_formatter.rb +3 -4
  471. data/lib/rubocop/formatter/formatter_set.rb +3 -1
  472. data/lib/rubocop/formatter/html_formatter.rb +1 -1
  473. data/lib/rubocop/formatter/json_formatter.rb +9 -3
  474. data/lib/rubocop/formatter/offense_count_formatter.rb +2 -0
  475. data/lib/rubocop/formatter/quiet_formatter.rb +13 -0
  476. data/lib/rubocop/formatter/simple_text_formatter.rb +3 -3
  477. data/lib/rubocop/formatter/tap_formatter.rb +71 -0
  478. data/lib/rubocop/formatter/worst_offenders_formatter.rb +2 -0
  479. data/lib/rubocop/node_pattern.rb +46 -29
  480. data/lib/rubocop/options.rb +13 -8
  481. data/lib/rubocop/path_util.rb +15 -3
  482. data/lib/rubocop/processed_source.rb +8 -9
  483. data/lib/rubocop/rake_task.rb +16 -23
  484. data/lib/rubocop/remote_config.rb +13 -1
  485. data/lib/rubocop/result_cache.rb +1 -0
  486. data/lib/rubocop/rspec/cop_helper.rb +10 -10
  487. data/lib/rubocop/rspec/expect_offense.rb +6 -8
  488. data/lib/rubocop/rspec/shared_contexts.rb +4 -8
  489. data/lib/rubocop/rspec/shared_examples.rb +8 -8
  490. data/lib/rubocop/rspec/support.rb +5 -5
  491. data/lib/rubocop/runner.rb +1 -1
  492. data/lib/rubocop/string_util.rb +2 -0
  493. data/lib/rubocop/token.rb +74 -0
  494. data/lib/rubocop/version.rb +1 -1
  495. metadata +118 -48
  496. data/lib/rubocop/cop/layout/space_inside_brackets.rb +0 -20
  497. data/lib/rubocop/cop/lint/invalid_character_literal.rb +0 -41
  498. data/lib/rubocop/cop/mixin/access_modifier_node.rb +0 -41
  499. data/lib/rubocop/cop/mixin/on_method_def.rb +0 -44
  500. data/lib/rubocop/cop/mixin/space_inside.rb +0 -76
  501. data/lib/rubocop/cop/style/accessor_method_name.rb +0 -45
  502. data/lib/rubocop/cop/style/class_and_module_camel_case.rb +0 -29
  503. data/lib/rubocop/cop/style/constant_name.rb +0 -29
  504. data/lib/rubocop/cop/style/method_name.rb +0 -34
  505. data/lib/rubocop/cop/style/predicate_name.rb +0 -67
  506. data/lib/rubocop/cop/style/variable_name.rb +0 -39
@@ -0,0 +1,101 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RuboCop
4
+ module Cop
5
+ module Style
6
+ # This cop checks for trailing code after the method definition.
7
+ #
8
+ # @example
9
+ # # bad
10
+ # def some_method; do_stuff
11
+ # end
12
+ #
13
+ # def f(x); b = foo
14
+ # b[c: x]
15
+ # end
16
+ #
17
+ # # good
18
+ # def some_method
19
+ # do_stuff
20
+ # end
21
+ #
22
+ # def f(x)
23
+ # b = foo
24
+ # b[c: x]
25
+ # end
26
+ #
27
+ class TrailingBodyOnMethodDefinition < Cop
28
+ include AutocorrectAlignment
29
+
30
+ MSG = "Place the first line of a multi-line method definition's " \
31
+ 'body on its own line.'.freeze
32
+
33
+ def on_def(node)
34
+ return unless trailing_body?(node)
35
+
36
+ add_offense(node, location: first_part_of(node.body))
37
+ end
38
+ alias on_defs on_def
39
+
40
+ def autocorrect(node)
41
+ lambda do |corrector|
42
+ break_line_before_body(node, corrector)
43
+ move_comment(node, corrector)
44
+ remove_semicolon(corrector)
45
+ end
46
+ end
47
+
48
+ private
49
+
50
+ def trailing_body?(node)
51
+ node.body && node.multiline? && on_def_line?(node)
52
+ end
53
+
54
+ def on_def_line?(node)
55
+ node.source_range.first_line == node.body.source_range.first_line
56
+ end
57
+
58
+ def break_line_before_body(node, corrector)
59
+ corrector.insert_before(
60
+ first_part_of(node.body),
61
+ "\n" + ' ' * (node.loc.keyword.column +
62
+ configured_indentation_width)
63
+ )
64
+ end
65
+
66
+ def first_part_of(body)
67
+ if body.begin_type?
68
+ body.children.first.source_range
69
+ else
70
+ body.source_range
71
+ end
72
+ end
73
+
74
+ def move_comment(node, corrector)
75
+ eol_comment = end_of_line_comment(node.source_range.line)
76
+ return unless eol_comment
77
+
78
+ text = eol_comment.loc.expression.source
79
+ corrector.insert_before(node.source_range,
80
+ text + "\n" + (' ' * node.loc.keyword.column))
81
+ corrector.remove(eol_comment.loc.expression)
82
+ end
83
+
84
+ def end_of_line_comment(line)
85
+ processed_source.comments.find { |c| c.loc.line == line }
86
+ end
87
+
88
+ def remove_semicolon(corrector)
89
+ return unless semicolon
90
+ corrector.remove(semicolon.pos)
91
+ end
92
+
93
+ def semicolon
94
+ @semicolon ||= processed_source.tokens.find do |token|
95
+ token.line == 1 && token.semicolon?
96
+ end
97
+ end
98
+ end
99
+ end
100
+ end
101
+ end
@@ -5,23 +5,37 @@ module RuboCop
5
5
  module Style
6
6
  # This cop checks for trailing comma in argument lists.
7
7
  #
8
- # @example
9
- # # always bad
8
+ # @example EnforcedStyleForMultiline: consistent_comma
9
+ # # bad
10
10
  # method(1, 2,)
11
11
  #
12
- # # good if EnforcedStyleForMultiline is consistent_comma
12
+ # # good
13
13
  # method(
14
14
  # 1, 2,
15
15
  # 3,
16
16
  # )
17
17
  #
18
- # # good if EnforcedStyleForMultiline is comma or consistent_comma
18
+ # # good
19
19
  # method(
20
20
  # 1,
21
21
  # 2,
22
22
  # )
23
23
  #
24
- # # good if EnforcedStyleForMultiline is no_comma
24
+ # @example EnforcedStyleForMultiline: comma
25
+ # # bad
26
+ # method(1, 2,)
27
+ #
28
+ # # good
29
+ # method(
30
+ # 1,
31
+ # 2,
32
+ # )
33
+ #
34
+ # @example EnforcedStyleForMultiline: no_comma (default)
35
+ # # bad
36
+ # method(1, 2,)
37
+ #
38
+ # # good
25
39
  # method(
26
40
  # 1,
27
41
  # 2
@@ -32,7 +46,7 @@ module RuboCop
32
46
  def on_send(node)
33
47
  return unless node.arguments? && node.parenthesized?
34
48
 
35
- check(node, node.arguments, 'parameter of %s method call',
49
+ check(node, node.arguments, 'parameter of %<article>s method call',
36
50
  node.last_argument.source_range.end_pos,
37
51
  node.source_range.end_pos)
38
52
  end
@@ -5,23 +5,37 @@ module RuboCop
5
5
  module Style
6
6
  # This cop checks for trailing comma in array and hash literals.
7
7
  #
8
- # @example
9
- # # always bad
8
+ # @example EnforcedStyleForMultiline: consistent_comma
9
+ # # bad
10
10
  # a = [1, 2,]
11
11
  #
12
- # # good if EnforcedStyleForMultiline is consistent_comma
12
+ # # good
13
13
  # a = [
14
14
  # 1, 2,
15
15
  # 3,
16
16
  # ]
17
17
  #
18
- # # good if EnforcedStyleForMultiline is comma or consistent_comma
18
+ # # good
19
19
  # a = [
20
20
  # 1,
21
21
  # 2,
22
22
  # ]
23
23
  #
24
- # # good if EnforcedStyleForMultiline is no_comma
24
+ # @example EnforcedStyleForMultiline: comma
25
+ # # bad
26
+ # a = [1, 2,]
27
+ #
28
+ # # good
29
+ # a = [
30
+ # 1,
31
+ # 2,
32
+ # ]
33
+ #
34
+ # @example EnforcedStyleForMultiline: no_comma (default)
35
+ # # bad
36
+ # a = [1, 2,]
37
+ #
38
+ # # good
25
39
  # a = [
26
40
  # 1,
27
41
  # 2
@@ -31,11 +45,12 @@ module RuboCop
31
45
  include TrailingComma
32
46
 
33
47
  def on_array(node)
34
- check_literal(node, 'item of %s array') if node.square_brackets?
48
+ return unless node.square_brackets?
49
+ check_literal(node, 'item of %<article>s array')
35
50
  end
36
51
 
37
52
  def on_hash(node)
38
- check_literal(node, 'item of %s hash')
53
+ check_literal(node, 'item of %<article>s hash')
39
54
  end
40
55
 
41
56
  private
@@ -0,0 +1,95 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RuboCop
4
+ module Cop
5
+ module Style
6
+ # This cop checks for trailing code after the method definition.
7
+ #
8
+ # @example
9
+ # # bad
10
+ # def some_method
11
+ # do_stuff; end
12
+ #
13
+ # def do_this(x)
14
+ # baz.map { |b| b.this(x) } end
15
+ #
16
+ # def foo
17
+ # block do
18
+ # bar
19
+ # end end
20
+ #
21
+ # # good
22
+ # def some_method
23
+ # do_stuff
24
+ # end
25
+ #
26
+ # def do_this(x)
27
+ # baz.map { |b| b.this(x) }
28
+ # end
29
+ #
30
+ # def foo
31
+ # block do
32
+ # bar
33
+ # end
34
+ # end
35
+ #
36
+ class TrailingMethodEndStatement < Cop
37
+ include AutocorrectAlignment
38
+
39
+ MSG = 'Place the end statement of a multi-line method on ' \
40
+ 'its own line.'.freeze
41
+
42
+ def on_def(node)
43
+ return unless trailing_end?(node)
44
+
45
+ add_offense(node.to_a.last, location: end_token.pos)
46
+ end
47
+
48
+ def autocorrect(_node)
49
+ lambda do |corrector|
50
+ break_line_before_end(corrector)
51
+ remove_semicolon(corrector)
52
+ end
53
+ end
54
+
55
+ private
56
+
57
+ def trailing_end?(node)
58
+ node.body &&
59
+ node.multiline? &&
60
+ end_token &&
61
+ body_and_end_on_same_line?
62
+ end
63
+
64
+ def end_token
65
+ @end_token ||= processed_source.tokens.reverse.find do |token|
66
+ token.type == :kEND
67
+ end
68
+ end
69
+
70
+ def body_and_end_on_same_line?
71
+ end_token.line == token_before_end.line
72
+ end
73
+
74
+ def token_before_end
75
+ @token_before_end ||= begin
76
+ i = processed_source.tokens.index(end_token)
77
+ processed_source.tokens[i - 1]
78
+ end
79
+ end
80
+
81
+ def break_line_before_end(corrector)
82
+ corrector.insert_before(
83
+ end_token.pos,
84
+ "\n" + ' ' * configured_indentation_width
85
+ )
86
+ end
87
+
88
+ def remove_semicolon(corrector)
89
+ return unless token_before_end.semicolon?
90
+ corrector.remove(token_before_end.pos)
91
+ end
92
+ end
93
+ end
94
+ end
95
+ end
@@ -15,8 +15,10 @@ module RuboCop
15
15
  # # good
16
16
  # a, b, = foo()
17
17
  # a, = foo()
18
- # *a, b, _ = foo() => We need to know to not include 2 variables in a
19
- # a, *b, _ = foo() => The correction `a, *b, = foo()` is a syntax error
18
+ # *a, b, _ = foo()
19
+ # # => We need to know to not include 2 variables in a
20
+ # a, *b, _ = foo()
21
+ # # => The correction `a, *b, = foo()` is a syntax error
20
22
  #
21
23
  # # good if AllowNamedUnderscoreVariables is true
22
24
  # a, b, _something = foo()
@@ -24,26 +26,28 @@ module RuboCop
24
26
  include SurroundingSpace
25
27
 
26
28
  MSG = 'Do not use trailing `_`s in parallel assignment. ' \
27
- 'Prefer `%s`.'.freeze
29
+ 'Prefer `%<code>s`.'.freeze
28
30
  UNDERSCORE = '_'.freeze
29
31
 
30
32
  def on_masgn(node)
31
- range = unneeded_range(node)
33
+ ranges = unneeded_ranges(node)
32
34
 
33
- return unless range
35
+ ranges.each do |range|
36
+ good_code = node.source
37
+ offset = range.begin_pos - node.source_range.begin_pos
38
+ good_code[offset, range.size] = ''
34
39
 
35
- good_code = node.source
36
- offset = range.begin_pos - node.source_range.begin_pos
37
- good_code[offset, range.size] = ''
38
-
39
- add_offense(node, range, format(MSG, good_code))
40
+ add_offense(node,
41
+ location: range,
42
+ message: format(MSG, code: good_code))
43
+ end
40
44
  end
41
45
 
42
46
  def autocorrect(node)
43
- range = unneeded_range(node)
47
+ ranges = unneeded_ranges(node)
44
48
 
45
49
  lambda do |corrector|
46
- corrector.remove(range) if range
50
+ ranges.each { |range| corrector.remove(range) if range }
47
51
  end
48
52
  end
49
53
 
@@ -60,6 +64,7 @@ module RuboCop
60
64
 
61
65
  def find_first_possible_offense(variables)
62
66
  variables.reduce(nil) do |offense, variable|
67
+ break offense unless %i[lvasgn splat].include?(variable.type)
63
68
  var, = *variable
64
69
  var, = *var
65
70
  if allow_named_underscore_variables
@@ -89,23 +94,64 @@ module RuboCop
89
94
  cop_config['AllowNamedUnderscoreVariables']
90
95
  end
91
96
 
92
- def unneeded_range(node)
93
- left, right = *node
94
- variables = *left
97
+ def unneeded_ranges(node)
98
+ node.masgn_type? ? (mlhs_node, = *node) : mlhs_node = node
99
+ variables = *mlhs_node
100
+
101
+ main_offense = main_node_offense(node)
102
+ if main_offense.nil?
103
+ children_offenses(variables)
104
+ else
105
+ children_offenses(variables) << main_offense
106
+ end
107
+ end
108
+
109
+ def main_node_offense(node)
110
+ node.masgn_type? ? (mlhs_node, right = *node) : mlhs_node = node
111
+
112
+ variables = *mlhs_node
95
113
  first_offense = find_first_offense(variables)
96
114
 
97
115
  return unless first_offense
98
116
 
99
- end_position =
100
- if first_offense.source_range == variables.first.source_range
101
- right.source_range.begin_pos
102
- else
103
- node.loc.operator.begin_pos
104
- end
117
+ if unused_variables_only?(first_offense, variables)
118
+ return unused_range(node.type, mlhs_node, right)
119
+ end
120
+
121
+ if Util.parentheses?(mlhs_node)
122
+ return range_for_parentheses(first_offense, mlhs_node)
123
+ end
124
+
125
+ range_between(first_offense.source_range.begin_pos,
126
+ node.loc.operator.begin_pos)
127
+ end
128
+
129
+ def children_offenses(variables)
130
+ variables.select(&:mlhs_type?).flat_map { |v| unneeded_ranges(v) }
131
+ end
132
+
133
+ def unused_variables_only?(offense, variables)
134
+ offense.source_range == variables.first.source_range
135
+ end
136
+
137
+ def unused_range(node_type, mlhs_node, right)
138
+ start_range = mlhs_node.source_range.begin_pos
139
+
140
+ end_range = case node_type
141
+ when :masgn
142
+ right.source_range.begin_pos
143
+ when :mlhs
144
+ mlhs_node.source_range.end_pos
145
+ end
146
+
147
+ range_between(start_range, end_range)
148
+ end
105
149
 
106
- range = range_between(first_offense.source_range.begin_pos,
107
- end_position)
108
- range_with_surrounding_space(range, :right)
150
+ def range_for_parentheses(offense, left)
151
+ range_between(
152
+ offense.source_range.begin_pos - 1,
153
+ left.loc.expression.end_pos - 1
154
+ )
109
155
  end
110
156
  end
111
157
  end
@@ -5,20 +5,45 @@ module RuboCop
5
5
  module Style
6
6
  # This cop looks for trivial reader/writer methods, that could
7
7
  # have been created with the attr_* family of functions automatically.
8
+ #
9
+ # @example
10
+ # # bad
11
+ # def foo
12
+ # @foo
13
+ # end
14
+ #
15
+ # def bar=(val)
16
+ # @bar = val
17
+ # end
18
+ #
19
+ # def self.baz
20
+ # @baz
21
+ # end
22
+ #
23
+ # # good
24
+ # attr_reader :foo
25
+ # attr_writer :bar
26
+ #
27
+ # class << self
28
+ # attr_reader :baz
29
+ # end
8
30
  class TrivialAccessors < Cop
9
- MSG = 'Use `attr_%s` to define trivial %s methods.'.freeze
31
+ MSG = 'Use `attr_%<kind>s` to define trivial %<kind>s methods.'.freeze
10
32
 
11
33
  def on_def(node)
12
34
  return if in_module_or_instance_eval?(node)
13
- method_name, args, body = *node
14
- on_method_def(node, method_name, args, body)
35
+ return if ignore_class_methods? && node.defs_type?
36
+
37
+ on_method_def(node)
15
38
  end
39
+ alias on_defs on_def
16
40
 
17
- def on_defs(node)
18
- return if in_module_or_instance_eval?(node)
19
- return if ignore_class_methods?
20
- _scope, method_name, args, body = *node
21
- on_method_def(node, method_name, args, body)
41
+ def autocorrect(node)
42
+ if node.def_type?
43
+ autocorrect_instance(node)
44
+ elsif node.defs_type? && node.children.first.self_type?
45
+ autocorrect_class(node)
46
+ end
22
47
  end
23
48
 
24
49
  private
@@ -37,15 +62,17 @@ module RuboCop
37
62
  false
38
63
  end
39
64
 
40
- def on_method_def(node, method_name, args, body)
41
- kind = if trivial_reader?(method_name, args, body)
65
+ def on_method_def(node)
66
+ kind = if trivial_reader?(node)
42
67
  'reader'
43
- elsif trivial_writer?(method_name, args, body)
68
+ elsif trivial_writer?(node)
44
69
  'writer'
45
70
  end
46
71
  return unless kind
47
72
 
48
- add_offense(node, :keyword, format(MSG, kind, kind))
73
+ add_offense(node,
74
+ location: :keyword,
75
+ message: format(MSG, kind: kind))
49
76
  end
50
77
 
51
78
  def exact_name_match?
@@ -69,61 +96,53 @@ module RuboCop
69
96
  Array(whitelist).map(&:to_sym) + [:initialize]
70
97
  end
71
98
 
72
- def predicate?(method_name)
73
- method_name[-1] == '?'
74
- end
75
-
76
99
  def dsl_writer?(method_name)
77
100
  !method_name.to_s.end_with?('=')
78
101
  end
79
102
 
80
- def trivial_reader?(method_name, args, body)
81
- looks_like_trivial_reader?(args, body) &&
82
- !allowed_method?(method_name, body) &&
83
- !allowed_reader?(method_name)
103
+ def trivial_reader?(node)
104
+ looks_like_trivial_reader?(node) &&
105
+ !allowed_method?(node) && !allowed_reader?(node)
84
106
  end
85
107
 
86
- def looks_like_trivial_reader?(args, body)
87
- args.children.empty? && body && body.ivar_type?
108
+ def looks_like_trivial_reader?(node)
109
+ !node.arguments? && node.body && node.body.ivar_type?
88
110
  end
89
111
 
90
- def trivial_writer?(method_name, args, body)
91
- looks_like_trivial_writer?(args, body) &&
92
- !allowed_method?(method_name, body) &&
93
- !allowed_writer?(method_name)
112
+ def trivial_writer?(node)
113
+ looks_like_trivial_writer?(node) &&
114
+ !allowed_method?(node) && !allowed_writer?(node.method_name)
94
115
  end
95
116
 
96
- def looks_like_trivial_writer?(args, body)
97
- args.children.one? &&
98
- !%i[restarg blockarg].include?(args.children[0].type) &&
99
- body && body.ivasgn_type? &&
100
- body.children[1] && body.children[1].lvar_type?
101
- end
117
+ def_node_matcher :looks_like_trivial_writer?, <<-PATTERN
118
+ {(def _ (args (arg ...)) (ivasgn _ (lvar _)))
119
+ (defs _ _ (args (arg ...)) (ivasgn _ (lvar _)))}
120
+ PATTERN
102
121
 
103
- def allowed_method?(method_name, body)
104
- whitelist.include?(method_name) ||
105
- exact_name_match? && !names_match?(method_name, body)
122
+ def allowed_method?(node)
123
+ whitelist.include?(node.method_name) ||
124
+ exact_name_match? && !names_match?(node)
106
125
  end
107
126
 
108
127
  def allowed_writer?(method_name)
109
128
  allow_dsl_writers? && dsl_writer?(method_name)
110
129
  end
111
130
 
112
- def allowed_reader?(method_name)
113
- allow_predicates? && predicate?(method_name)
131
+ def allowed_reader?(node)
132
+ allow_predicates? && node.predicate_method?
114
133
  end
115
134
 
116
- def names_match?(method_name, body)
117
- ivar_name, = *body
135
+ def names_match?(node)
136
+ ivar_name, = *node.body
118
137
 
119
- method_name.to_s.sub(/[=?]$/, '') == ivar_name[1..-1]
138
+ node.method_name.to_s.sub(/[=?]$/, '') == ivar_name[1..-1]
120
139
  end
121
140
 
122
- def trivial_accessor_kind(method_name, args, body)
123
- if trivial_writer?(method_name, args, body) &&
124
- !dsl_writer?(method_name)
141
+ def trivial_accessor_kind(node)
142
+ if trivial_writer?(node) &&
143
+ !dsl_writer?(node.method_name)
125
144
  'writer'
126
- elsif trivial_reader?(method_name, args, body)
145
+ elsif trivial_reader?(node)
127
146
  'reader'
128
147
  end
129
148
  end
@@ -132,40 +151,28 @@ module RuboCop
132
151
  "attr_#{kind} :#{method_name.to_s.chomp('=')}"
133
152
  end
134
153
 
135
- def autocorrect(node)
136
- if node.def_type?
137
- autocorrect_instance(node)
138
- elsif node.defs_type? && node.children.first.self_type?
139
- autocorrect_class(node)
140
- end
141
- end
142
-
143
154
  def autocorrect_instance(node)
144
- method_name, args, body = *node
145
- unless names_match?(method_name, body) &&
146
- !predicate?(method_name) &&
147
- (kind = trivial_accessor_kind(method_name, args, body))
148
- return
149
- end
155
+ kind = trivial_accessor_kind(node)
156
+
157
+ return unless names_match?(node) && !node.predicate_method? && kind
150
158
 
151
159
  lambda do |corrector|
152
- corrector.replace(node.source_range, accessor(kind, method_name))
160
+ corrector.replace(node.source_range,
161
+ accessor(kind, node.method_name))
153
162
  end
154
163
  end
155
164
 
156
165
  def autocorrect_class(node)
157
- _, method_name, args, body = *node
158
- unless names_match?(method_name, body) &&
159
- (kind = trivial_accessor_kind(method_name, args, body))
160
- return
161
- end
166
+ kind = trivial_accessor_kind(node)
167
+
168
+ return unless names_match?(node) && kind
162
169
 
163
170
  lambda do |corrector|
164
171
  indent = ' ' * node.loc.column
165
172
  corrector.replace(
166
173
  node.source_range,
167
174
  ['class << self',
168
- "#{indent} #{accessor(kind, method_name)}",
175
+ "#{indent} #{accessor(kind, node.method_name)}",
169
176
  "#{indent}end"].join("\n")
170
177
  )
171
178
  end