rubocop 0.72.0 → 0.76.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 (249) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +2 -1
  3. data/bin/console +1 -0
  4. data/config/default.yml +93 -56
  5. data/lib/rubocop.rb +21 -10
  6. data/lib/rubocop/ast/builder.rb +1 -0
  7. data/lib/rubocop/ast/node.rb +12 -14
  8. data/lib/rubocop/ast/node/mixin/method_dispatch_node.rb +4 -4
  9. data/lib/rubocop/ast/node/return_node.rb +24 -0
  10. data/lib/rubocop/ast/traversal.rb +3 -3
  11. data/lib/rubocop/cli.rb +7 -4
  12. data/lib/rubocop/comment_config.rb +5 -4
  13. data/lib/rubocop/config.rb +28 -537
  14. data/lib/rubocop/config_loader.rb +21 -3
  15. data/lib/rubocop/config_loader_resolver.rb +4 -3
  16. data/lib/rubocop/config_obsoletion.rb +222 -0
  17. data/lib/rubocop/config_validator.rb +248 -0
  18. data/lib/rubocop/cop/autocorrect_logic.rb +71 -1
  19. data/lib/rubocop/cop/bundler/insecure_protocol_source.rb +1 -1
  20. data/lib/rubocop/cop/bundler/ordered_gems.rb +1 -1
  21. data/lib/rubocop/cop/commissioner.rb +18 -16
  22. data/lib/rubocop/cop/cop.rb +49 -14
  23. data/lib/rubocop/cop/corrector.rb +10 -10
  24. data/lib/rubocop/cop/correctors/alignment_corrector.rb +43 -17
  25. data/lib/rubocop/cop/correctors/empty_line_corrector.rb +2 -2
  26. data/lib/rubocop/cop/correctors/multiline_literal_brace_corrector.rb +2 -2
  27. data/lib/rubocop/cop/correctors/percent_literal_corrector.rb +1 -1
  28. data/lib/rubocop/cop/gemspec/duplicated_assignment.rb +2 -2
  29. data/lib/rubocop/cop/gemspec/ordered_dependencies.rb +1 -1
  30. data/lib/rubocop/cop/gemspec/required_ruby_version.rb +1 -1
  31. data/lib/rubocop/cop/gemspec/ruby_version_globals_usage.rb +1 -1
  32. data/lib/rubocop/cop/generator.rb +4 -4
  33. data/lib/rubocop/cop/generator/configuration_injector.rb +9 -4
  34. data/lib/rubocop/cop/generator/require_file_injector.rb +1 -1
  35. data/lib/rubocop/cop/internal_affairs/node_destructuring.rb +2 -2
  36. data/lib/rubocop/cop/internal_affairs/node_type_predicate.rb +1 -1
  37. data/lib/rubocop/cop/internal_affairs/offense_location_keyword.rb +2 -2
  38. data/lib/rubocop/cop/internal_affairs/redundant_location_argument.rb +1 -1
  39. data/lib/rubocop/cop/internal_affairs/redundant_message_argument.rb +2 -2
  40. data/lib/rubocop/cop/internal_affairs/useless_message_assertion.rb +2 -2
  41. data/lib/rubocop/cop/layout/align_hash.rb +6 -2
  42. data/lib/rubocop/cop/layout/block_alignment.rb +3 -3
  43. data/lib/rubocop/cop/layout/class_structure.rb +1 -1
  44. data/lib/rubocop/cop/layout/closing_parenthesis_indentation.rb +1 -1
  45. data/lib/rubocop/cop/layout/comment_indentation.rb +10 -13
  46. data/lib/rubocop/cop/layout/empty_comment.rb +7 -16
  47. data/lib/rubocop/cop/layout/empty_line_after_guard_clause.rb +22 -7
  48. data/lib/rubocop/cop/layout/empty_line_after_magic_comment.rb +2 -2
  49. data/lib/rubocop/cop/layout/empty_lines_around_class_body.rb +2 -2
  50. data/lib/rubocop/cop/layout/end_of_line.rb +8 -3
  51. data/lib/rubocop/cop/layout/extra_spacing.rb +14 -59
  52. data/lib/rubocop/cop/layout/indent_assignment.rb +10 -1
  53. data/lib/rubocop/cop/layout/indent_first_argument.rb +10 -8
  54. data/lib/rubocop/cop/layout/indent_first_hash_element.rb +1 -1
  55. data/lib/rubocop/cop/layout/indent_heredoc.rb +4 -3
  56. data/lib/rubocop/cop/layout/indentation_width.rb +20 -6
  57. data/lib/rubocop/cop/layout/leading_comment_space.rb +28 -0
  58. data/lib/rubocop/cop/layout/multiline_assignment_layout.rb +1 -1
  59. data/lib/rubocop/cop/layout/multiline_block_layout.rb +24 -2
  60. data/lib/rubocop/cop/layout/rescue_ensure_alignment.rb +20 -4
  61. data/lib/rubocop/cop/layout/space_around_block_parameters.rb +5 -1
  62. data/lib/rubocop/cop/layout/space_around_operators.rb +42 -23
  63. data/lib/rubocop/cop/layout/space_in_lambda_literal.rb +9 -7
  64. data/lib/rubocop/cop/layout/space_inside_array_literal_brackets.rb +8 -5
  65. data/lib/rubocop/cop/layout/space_inside_block_braces.rb +21 -2
  66. data/lib/rubocop/cop/layout/space_inside_parens.rb +6 -6
  67. data/lib/rubocop/cop/layout/space_inside_string_interpolation.rb +24 -40
  68. data/lib/rubocop/cop/layout/tab.rb +10 -22
  69. data/lib/rubocop/cop/layout/trailing_whitespace.rb +18 -2
  70. data/lib/rubocop/cop/lint/assignment_in_condition.rb +17 -4
  71. data/lib/rubocop/cop/lint/big_decimal_new.rb +1 -1
  72. data/lib/rubocop/cop/lint/debugger.rb +4 -6
  73. data/lib/rubocop/cop/lint/duplicate_methods.rb +3 -3
  74. data/lib/rubocop/cop/lint/each_with_object_argument.rb +1 -1
  75. data/lib/rubocop/cop/lint/empty_interpolation.rb +4 -4
  76. data/lib/rubocop/cop/lint/erb_new_arguments.rb +62 -5
  77. data/lib/rubocop/cop/lint/format_parameter_mismatch.rb +11 -37
  78. data/lib/rubocop/cop/lint/ineffective_access_modifier.rb +1 -1
  79. data/lib/rubocop/cop/lint/inherit_exception.rb +1 -1
  80. data/lib/rubocop/cop/lint/literal_in_interpolation.rb +7 -8
  81. data/lib/rubocop/cop/lint/missing_cop_enable_directive.rb +2 -2
  82. data/lib/rubocop/cop/lint/multiple_compare.rb +1 -1
  83. data/lib/rubocop/cop/lint/nested_method_definition.rb +3 -3
  84. data/lib/rubocop/cop/lint/next_without_accumulator.rb +1 -1
  85. data/lib/rubocop/cop/lint/non_local_exit_from_iterator.rb +1 -1
  86. data/lib/rubocop/cop/lint/number_conversion.rb +3 -3
  87. data/lib/rubocop/cop/lint/rand_one.rb +1 -1
  88. data/lib/rubocop/cop/lint/{unneeded_cop_disable_directive.rb → redundant_cop_disable_directive.rb} +24 -24
  89. data/lib/rubocop/cop/lint/{unneeded_cop_enable_directive.rb → redundant_cop_enable_directive.rb} +6 -8
  90. data/lib/rubocop/cop/lint/{unneeded_require_statement.rb → redundant_require_statement.rb} +2 -2
  91. data/lib/rubocop/cop/lint/{unneeded_splat_expansion.rb → redundant_splat_expansion.rb} +12 -7
  92. data/lib/rubocop/cop/lint/redundant_with_index.rb +1 -1
  93. data/lib/rubocop/cop/lint/redundant_with_object.rb +1 -1
  94. data/lib/rubocop/cop/lint/safe_navigation_chain.rb +10 -11
  95. data/lib/rubocop/cop/lint/safe_navigation_with_empty.rb +1 -1
  96. data/lib/rubocop/cop/lint/send_with_mixin_argument.rb +91 -0
  97. data/lib/rubocop/cop/lint/string_conversion_in_interpolation.rb +6 -6
  98. data/lib/rubocop/cop/lint/unified_integer.rb +1 -1
  99. data/lib/rubocop/cop/lint/unreachable_code.rb +1 -1
  100. data/lib/rubocop/cop/lint/unused_block_argument.rb +22 -6
  101. data/lib/rubocop/cop/lint/unused_method_argument.rb +23 -5
  102. data/lib/rubocop/cop/lint/uri_escape_unescape.rb +1 -1
  103. data/lib/rubocop/cop/lint/uri_regexp.rb +2 -2
  104. data/lib/rubocop/cop/lint/useless_access_modifier.rb +6 -6
  105. data/lib/rubocop/cop/lint/useless_setter_call.rb +1 -1
  106. data/lib/rubocop/cop/lint/void.rb +7 -26
  107. data/lib/rubocop/cop/message_annotator.rb +16 -7
  108. data/lib/rubocop/cop/metrics/abc_size.rb +1 -1
  109. data/lib/rubocop/cop/metrics/class_length.rb +1 -1
  110. data/lib/rubocop/cop/metrics/line_length.rb +7 -4
  111. data/lib/rubocop/cop/metrics/module_length.rb +1 -1
  112. data/lib/rubocop/cop/metrics/parameter_lists.rb +1 -1
  113. data/lib/rubocop/cop/metrics/utils/abc_size_calculator.rb +23 -6
  114. data/lib/rubocop/cop/migration/department_name.rb +44 -0
  115. data/lib/rubocop/cop/mixin/alignment.rb +1 -1
  116. data/lib/rubocop/cop/mixin/def_node.rb +1 -1
  117. data/lib/rubocop/cop/mixin/documentation_comment.rb +0 -2
  118. data/lib/rubocop/cop/mixin/empty_parameter.rb +1 -1
  119. data/lib/rubocop/cop/mixin/enforce_superclass.rb +4 -4
  120. data/lib/rubocop/cop/mixin/frozen_string_literal.rb +1 -1
  121. data/lib/rubocop/cop/mixin/interpolation.rb +27 -0
  122. data/lib/rubocop/cop/mixin/method_complexity.rb +3 -2
  123. data/lib/rubocop/cop/mixin/multiline_expression_indentation.rb +3 -3
  124. data/lib/rubocop/cop/mixin/preceding_following_alignment.rb +87 -0
  125. data/lib/rubocop/cop/mixin/safe_mode.rb +2 -0
  126. data/lib/rubocop/cop/mixin/statement_modifier.rb +5 -2
  127. data/lib/rubocop/cop/mixin/surrounding_space.rb +7 -5
  128. data/lib/rubocop/cop/mixin/trailing_comma.rb +8 -6
  129. data/lib/rubocop/cop/naming/binary_operator_parameter_name.rb +1 -1
  130. data/lib/rubocop/cop/naming/constant_name.rb +2 -2
  131. data/lib/rubocop/cop/naming/file_name.rb +12 -5
  132. data/lib/rubocop/cop/naming/method_name.rb +12 -1
  133. data/lib/rubocop/cop/naming/predicate_name.rb +1 -1
  134. data/lib/rubocop/cop/naming/variable_name.rb +1 -0
  135. data/lib/rubocop/cop/offense.rb +18 -7
  136. data/lib/rubocop/cop/registry.rb +22 -1
  137. data/lib/rubocop/cop/security/eval.rb +1 -1
  138. data/lib/rubocop/cop/security/json_load.rb +1 -1
  139. data/lib/rubocop/cop/security/marshal_load.rb +1 -1
  140. data/lib/rubocop/cop/security/open.rb +1 -1
  141. data/lib/rubocop/cop/security/yaml_load.rb +1 -1
  142. data/lib/rubocop/cop/style/access_modifier_declarations.rb +1 -0
  143. data/lib/rubocop/cop/style/alias.rb +1 -1
  144. data/lib/rubocop/cop/style/attr.rb +2 -2
  145. data/lib/rubocop/cop/style/block_delimiters.rb +2 -1
  146. data/lib/rubocop/cop/style/braces_around_hash_parameters.rb +35 -16
  147. data/lib/rubocop/cop/style/class_and_module_children.rb +1 -1
  148. data/lib/rubocop/cop/style/colon_method_call.rb +1 -1
  149. data/lib/rubocop/cop/style/comment_annotation.rb +5 -5
  150. data/lib/rubocop/cop/style/commented_keyword.rb +16 -30
  151. data/lib/rubocop/cop/style/conditional_assignment.rb +6 -8
  152. data/lib/rubocop/cop/style/constant_visibility.rb +14 -3
  153. data/lib/rubocop/cop/style/copyright.rb +11 -7
  154. data/lib/rubocop/cop/style/date_time.rb +3 -3
  155. data/lib/rubocop/cop/style/dir.rb +1 -1
  156. data/lib/rubocop/cop/style/documentation_method.rb +45 -1
  157. data/lib/rubocop/cop/style/double_cop_disable_directive.rb +55 -0
  158. data/lib/rubocop/cop/style/each_for_simple_loop.rb +1 -1
  159. data/lib/rubocop/cop/style/each_with_object.rb +1 -1
  160. data/lib/rubocop/cop/style/empty_case_condition.rb +2 -2
  161. data/lib/rubocop/cop/style/empty_literal.rb +2 -2
  162. data/lib/rubocop/cop/style/empty_method.rb +5 -5
  163. data/lib/rubocop/cop/style/eval_with_location.rb +2 -2
  164. data/lib/rubocop/cop/style/even_odd.rb +1 -1
  165. data/lib/rubocop/cop/style/expand_path_arguments.rb +4 -4
  166. data/lib/rubocop/cop/style/float_division.rb +4 -4
  167. data/lib/rubocop/cop/style/format_string.rb +17 -14
  168. data/lib/rubocop/cop/style/format_string_token.rb +19 -68
  169. data/lib/rubocop/cop/style/frozen_string_literal_comment.rb +28 -33
  170. data/lib/rubocop/cop/style/guard_clause.rb +39 -10
  171. data/lib/rubocop/cop/style/hash_syntax.rb +4 -4
  172. data/lib/rubocop/cop/style/if_unless_modifier.rb +58 -15
  173. data/lib/rubocop/cop/style/infinite_loop.rb +5 -4
  174. data/lib/rubocop/cop/style/inverse_methods.rb +21 -15
  175. data/lib/rubocop/cop/style/lambda.rb +0 -2
  176. data/lib/rubocop/cop/style/line_end_concatenation.rb +14 -10
  177. data/lib/rubocop/cop/style/method_call_with_args_parentheses.rb +25 -25
  178. data/lib/rubocop/cop/style/method_def_parentheses.rb +17 -9
  179. data/lib/rubocop/cop/style/min_max.rb +1 -1
  180. data/lib/rubocop/cop/style/mixin_usage.rb +12 -2
  181. data/lib/rubocop/cop/style/multiline_memoization.rb +1 -1
  182. data/lib/rubocop/cop/style/multiline_when_then.rb +55 -0
  183. data/lib/rubocop/cop/style/multiple_comparison.rb +1 -1
  184. data/lib/rubocop/cop/style/mutable_constant.rb +3 -3
  185. data/lib/rubocop/cop/style/nested_modifier.rb +22 -4
  186. data/lib/rubocop/cop/style/non_nil_check.rb +21 -9
  187. data/lib/rubocop/cop/style/numeric_predicate.rb +3 -3
  188. data/lib/rubocop/cop/style/option_hash.rb +1 -1
  189. data/lib/rubocop/cop/style/or_assignment.rb +8 -3
  190. data/lib/rubocop/cop/style/parentheses_around_condition.rb +15 -1
  191. data/lib/rubocop/cop/style/random_with_offset.rb +6 -6
  192. data/lib/rubocop/cop/style/{unneeded_capital_w.rb → redundant_capital_w.rb} +1 -1
  193. data/lib/rubocop/cop/style/{unneeded_condition.rb → redundant_condition.rb} +3 -3
  194. data/lib/rubocop/cop/style/redundant_conditional.rb +2 -2
  195. data/lib/rubocop/cop/style/redundant_exception.rb +2 -2
  196. data/lib/rubocop/cop/style/redundant_freeze.rb +1 -1
  197. data/lib/rubocop/cop/style/{unneeded_interpolation.rb → redundant_interpolation.rb} +1 -1
  198. data/lib/rubocop/cop/style/redundant_parentheses.rb +15 -6
  199. data/lib/rubocop/cop/style/{unneeded_percent_q.rb → redundant_percent_q.rb} +1 -1
  200. data/lib/rubocop/cop/style/redundant_return.rb +37 -21
  201. data/lib/rubocop/cop/style/redundant_self.rb +18 -1
  202. data/lib/rubocop/cop/style/{unneeded_sort.rb → redundant_sort.rb} +4 -4
  203. data/lib/rubocop/cop/style/redundant_sort_by.rb +1 -1
  204. data/lib/rubocop/cop/style/rescue_modifier.rb +24 -0
  205. data/lib/rubocop/cop/style/rescue_standard_error.rb +2 -2
  206. data/lib/rubocop/cop/style/return_nil.rb +1 -1
  207. data/lib/rubocop/cop/style/safe_navigation.rb +24 -4
  208. data/lib/rubocop/cop/style/sample.rb +1 -1
  209. data/lib/rubocop/cop/style/semicolon.rb +13 -2
  210. data/lib/rubocop/cop/style/single_line_methods.rb +8 -1
  211. data/lib/rubocop/cop/style/special_global_vars.rb +5 -7
  212. data/lib/rubocop/cop/style/stderr_puts.rb +1 -1
  213. data/lib/rubocop/cop/style/string_hash_keys.rb +2 -2
  214. data/lib/rubocop/cop/style/strip.rb +1 -1
  215. data/lib/rubocop/cop/style/struct_inheritance.rb +3 -3
  216. data/lib/rubocop/cop/style/symbol_proc.rb +1 -1
  217. data/lib/rubocop/cop/style/ternary_parentheses.rb +20 -1
  218. data/lib/rubocop/cop/style/trailing_method_end_statement.rb +4 -6
  219. data/lib/rubocop/cop/style/trivial_accessors.rb +1 -1
  220. data/lib/rubocop/cop/style/unpack_first.rb +1 -1
  221. data/lib/rubocop/cop/style/variable_interpolation.rb +6 -16
  222. data/lib/rubocop/cop/style/zero_length_predicate.rb +5 -5
  223. data/lib/rubocop/cop/team.rb +15 -14
  224. data/lib/rubocop/cop/util.rb +1 -1
  225. data/lib/rubocop/cop/utils/format_string.rb +120 -0
  226. data/lib/rubocop/cop/variable_force.rb +7 -5
  227. data/lib/rubocop/cop/variable_force/variable.rb +15 -2
  228. data/lib/rubocop/core_ext/string.rb +0 -24
  229. data/lib/rubocop/error.rb +23 -0
  230. data/lib/rubocop/formatter/clang_style_formatter.rb +8 -3
  231. data/lib/rubocop/formatter/emacs_style_formatter.rb +22 -9
  232. data/lib/rubocop/formatter/file_list_formatter.rb +1 -1
  233. data/lib/rubocop/formatter/formatter_set.rb +16 -15
  234. data/lib/rubocop/formatter/pacman_formatter.rb +80 -0
  235. data/lib/rubocop/formatter/simple_text_formatter.rb +16 -4
  236. data/lib/rubocop/formatter/tap_formatter.rb +17 -4
  237. data/lib/rubocop/magic_comment.rb +4 -0
  238. data/lib/rubocop/node_pattern.rb +5 -3
  239. data/lib/rubocop/options.rb +33 -21
  240. data/lib/rubocop/path_util.rb +1 -1
  241. data/lib/rubocop/processed_source.rb +4 -0
  242. data/lib/rubocop/result_cache.rb +1 -1
  243. data/lib/rubocop/rspec/expect_offense.rb +4 -1
  244. data/lib/rubocop/rspec/shared_contexts.rb +12 -0
  245. data/lib/rubocop/runner.rb +42 -31
  246. data/lib/rubocop/target_finder.rb +12 -4
  247. data/lib/rubocop/version.rb +1 -1
  248. metadata +21 -12
  249. data/lib/rubocop/cop/mixin/ignored_method_patterns.rb +0 -19
@@ -0,0 +1,44 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RuboCop
4
+ module Cop
5
+ module Migration
6
+ # Check that cop names in rubocop:disable comments are given with
7
+ # department name.
8
+ class DepartmentName < Cop
9
+ include RangeHelp
10
+
11
+ MSG = 'Department name is missing.'
12
+
13
+ def investigate(processed_source)
14
+ processed_source.each_comment do |comment|
15
+ next if comment.text !~ /\A(# *rubocop:((dis|en)able|todo) +)(.*)/
16
+
17
+ offset = Regexp.last_match(1).length
18
+ Regexp.last_match(4).scan(%r{[\w/]+|\W+}) do |name|
19
+ check_cop_name(name, comment, offset)
20
+ offset += name.length
21
+ end
22
+ end
23
+ end
24
+
25
+ def autocorrect(range)
26
+ shall_warn = false
27
+ qualified_cop_name = Cop.registry.qualified_cop_name(range.source,
28
+ nil, shall_warn)
29
+ ->(corrector) { corrector.replace(range, qualified_cop_name) }
30
+ end
31
+
32
+ private
33
+
34
+ def check_cop_name(name, comment, offset)
35
+ return if name !~ /^[A-Z]/ || name =~ %r{/}
36
+
37
+ start = comment.location.expression.begin_pos + offset
38
+ range = range_between(start, start + name.length)
39
+ add_offense(range, location: range)
40
+ end
41
+ end
42
+ end
43
+ end
44
+ end
@@ -13,7 +13,7 @@ module RuboCop
13
13
 
14
14
  def configured_indentation_width
15
15
  cop_config['IndentationWidth'] ||
16
- config.for_cop('IndentationWidth')['Width']
16
+ config.for_cop('Layout/IndentationWidth')['Width']
17
17
  end
18
18
 
19
19
  def indentation(node)
@@ -25,7 +25,7 @@ module RuboCop
25
25
  processed_source[0..index].map(&:strip)
26
26
  end
27
27
 
28
- def_node_matcher :non_public_modifier?, <<-PATTERN
28
+ def_node_matcher :non_public_modifier?, <<~PATTERN
29
29
  (send nil? {:private :protected} ({def defs} ...))
30
30
  PATTERN
31
31
  end
@@ -9,8 +9,6 @@ module RuboCop
9
9
 
10
10
  private
11
11
 
12
- def_node_matcher :constant_definition?, '{class module casgn}'
13
-
14
12
  def documentation_comment?(node)
15
13
  preceding_lines = preceding_lines(node)
16
14
 
@@ -8,7 +8,7 @@ module RuboCop
8
8
 
9
9
  private
10
10
 
11
- def_node_matcher :empty_arguments?, <<-PATTERN
11
+ def_node_matcher :empty_arguments?, <<~PATTERN
12
12
  (block _ $(args) _)
13
13
  PATTERN
14
14
 
@@ -5,12 +5,12 @@ module RuboCop
5
5
  # Common functionality for enforcing a specific superclass
6
6
  module EnforceSuperclass
7
7
  def self.included(base)
8
- base.def_node_matcher :class_definition, <<-PATTERN
9
- (class (const _ !:#{base::SUPERCLASS}) #{base::BASE_PATTERN} ...)
8
+ base.def_node_matcher :class_definition, <<~PATTERN
9
+ (class (const _ !:#{base::SUPERCLASS}) #{base::BASE_PATTERN} ...)
10
10
  PATTERN
11
11
 
12
- base.def_node_matcher :class_new_definition, <<-PATTERN
13
- [!^(casgn nil? :#{base::SUPERCLASS} ...) (send (const nil? :Class) :new #{base::BASE_PATTERN})]
12
+ base.def_node_matcher :class_new_definition, <<~PATTERN
13
+ [!^(casgn nil? :#{base::SUPERCLASS} ...) (send (const nil? :Class) :new #{base::BASE_PATTERN})]
14
14
  PATTERN
15
15
  end
16
16
 
@@ -12,7 +12,7 @@ module RuboCop
12
12
 
13
13
  def frozen_string_literal_comment_exists?
14
14
  leading_comment_lines.any? do |line|
15
- MagicComment.parse(line).frozen_string_literal_specified?
15
+ MagicComment.parse(line).valid_literal_value?
16
16
  end
17
17
  end
18
18
 
@@ -0,0 +1,27 @@
1
+ # frozen_string_literal: true
2
+
3
+ module RuboCop
4
+ module Cop
5
+ # Common functionality for working with string interpolations.
6
+ #
7
+ # @abstract Subclasses are expected to implement {#on_interpolation}.
8
+ module Interpolation
9
+ def on_dstr(node)
10
+ on_node_with_interpolations(node)
11
+ end
12
+
13
+ alias on_xstr on_dstr
14
+ alias on_dsym on_dstr
15
+ alias on_regexp on_dstr
16
+
17
+ def on_node_with_interpolations(node)
18
+ node.each_child_node(:begin) do |begin_node|
19
+ on_interpolation(begin_node)
20
+ end
21
+ end
22
+
23
+ # @!method on_interpolation(begin_node)
24
+ # Inspect the `:begin` node of an interpolation
25
+ end
26
+ end
27
+ end
@@ -20,7 +20,7 @@ module RuboCop
20
20
 
21
21
  private
22
22
 
23
- def_node_matcher :define_method?, <<-PATTERN
23
+ def_node_matcher :define_method?, <<~PATTERN
24
24
  (block
25
25
  (send nil? :define_method ({sym str} $_))
26
26
  args
@@ -32,13 +32,14 @@ module RuboCop
32
32
  return unless node.body
33
33
 
34
34
  max = cop_config['Max']
35
- complexity = complexity(node.body)
35
+ complexity, abc_vector = complexity(node.body)
36
36
 
37
37
  return unless complexity > max
38
38
 
39
39
  msg = format(self.class::MSG,
40
40
  method: method_name,
41
41
  complexity: complexity,
42
+ abc_vector: abc_vector,
42
43
  max: max)
43
44
 
44
45
  add_offense(node, message: msg) do
@@ -159,11 +159,11 @@ module RuboCop
159
159
  break false if a.block_type?
160
160
 
161
161
  next if a.setter_method?
162
+ next unless kind == :with_or_without_parentheses ||
163
+ kind == :with_parentheses && parentheses?(a)
162
164
 
163
165
  a.arguments.any? do |arg|
164
- within_node?(node, arg) && (kind == :with_or_without_parentheses ||
165
- kind == :with_parentheses &&
166
- parentheses?(node.parent))
166
+ within_node?(node, arg)
167
167
  end
168
168
  end
169
169
  end
@@ -19,6 +19,18 @@ module RuboCop
19
19
  aligned_with_adjacent_line?(range, method(:aligned_operator?))
20
20
  end
21
21
 
22
+ def aligned_with_preceding_assignment(token)
23
+ preceding_line_range = token.line.downto(1)
24
+
25
+ aligned_with_assignment(token, preceding_line_range)
26
+ end
27
+
28
+ def aligned_with_subsequent_assignment(token)
29
+ subsequent_line_range = token.line.upto(processed_source.lines.length)
30
+
31
+ aligned_with_assignment(token, subsequent_line_range)
32
+ end
33
+
22
34
  def aligned_with_adjacent_line?(range, predicate)
23
35
  # minus 2 because node.loc.line is zero-based
24
36
  pre = (range.line - 2).downto(0)
@@ -89,6 +101,81 @@ module RuboCop
89
101
  def aligned_identical?(range, line)
90
102
  range.source == line[range.column, range.size]
91
103
  end
104
+
105
+ def aligned_with_assignment(token, line_range)
106
+ token_line_indent = processed_source
107
+ .line_indentation(token.line)
108
+ assignment_lines = relevant_assignment_lines(line_range)
109
+ relevant_line_number = assignment_lines[1]
110
+
111
+ return :none unless relevant_line_number
112
+
113
+ relevant_indent = processed_source
114
+ .line_indentation(relevant_line_number)
115
+
116
+ return :none if relevant_indent < token_line_indent
117
+
118
+ assignment_line = processed_source.lines[relevant_line_number - 1]
119
+
120
+ return :none unless assignment_line
121
+
122
+ aligned_assignment?(token.pos, assignment_line) ? :yes : :no
123
+ end
124
+
125
+ def assignment_lines
126
+ @assignment_lines ||= assignment_tokens.map(&:line)
127
+ end
128
+
129
+ def assignment_tokens
130
+ @assignment_tokens ||= begin
131
+ tokens = processed_source.tokens.select(&:equal_sign?)
132
+
133
+ # we don't want to operate on equals signs which are part of an
134
+ # optarg in a method definition
135
+ # e.g.: def method(optarg = default_val); end
136
+ tokens = remove_optarg_equals(tokens, processed_source)
137
+
138
+ # Only attempt to align the first = on each line
139
+ Set.new(tokens.uniq(&:line))
140
+ end
141
+ end
142
+
143
+ # rubocop:disable Metrics/AbcSize, Metrics/CyclomaticComplexity
144
+ # rubocop:disable Metrics/PerceivedComplexity, Metrics/MethodLength
145
+ def relevant_assignment_lines(line_range)
146
+ result = []
147
+ original_line_indent = processed_source
148
+ .line_indentation(line_range.first)
149
+ relevant_line_indent_at_level = true
150
+
151
+ line_range.each do |line_number|
152
+ current_line_indent = processed_source.line_indentation(line_number)
153
+ blank_line = processed_source.lines[line_number - 1].blank?
154
+
155
+ if (current_line_indent < original_line_indent && !blank_line) ||
156
+ (relevant_line_indent_at_level && blank_line)
157
+ break
158
+ end
159
+
160
+ result << line_number if assignment_lines.include?(line_number) &&
161
+ current_line_indent == original_line_indent
162
+
163
+ unless blank_line
164
+ relevant_line_indent_at_level = \
165
+ current_line_indent == original_line_indent
166
+ end
167
+ end
168
+
169
+ result
170
+ end
171
+ # rubocop:enable Metrics/AbcSize, Metrics/CyclomaticComplexity
172
+ # rubocop:enable Metrics/PerceivedComplexity, Metrics/MethodLength
173
+
174
+ def remove_optarg_equals(asgn_tokens, processed_source)
175
+ optargs = processed_source.ast.each_node(:optarg)
176
+ optarg_eql = optargs.map { |o| o.loc.operator.begin_pos }.to_set
177
+ asgn_tokens.reject { |t| optarg_eql.include?(t.begin_pos) }
178
+ end
92
179
  end
93
180
  end
94
181
  end
@@ -3,6 +3,8 @@
3
3
  module RuboCop
4
4
  module Cop
5
5
  # Common functionality for Rails safe mode.
6
+ #
7
+ # This module can be removed from RuboCop 0.76.
6
8
  module SafeMode
7
9
  private
8
10
 
@@ -41,10 +41,13 @@ module RuboCop
41
41
  end
42
42
 
43
43
  def length_in_modifier_form(node, cond, body_length)
44
- indentation = node.loc.keyword.column * indentation_multiplier
45
- kw_length = node.loc.keyword.size
44
+ keyword = node.loc.keyword
45
+
46
+ indentation = keyword.column * indentation_multiplier
47
+ kw_length = keyword.size
46
48
  cond_length = cond.source_range.size
47
49
  space = 1
50
+
48
51
  indentation + body_length + space + kw_length + space + cond_length
49
52
  end
50
53
 
@@ -9,6 +9,8 @@ module RuboCop
9
9
  NO_SPACE_COMMAND = 'Do not use'
10
10
  SPACE_COMMAND = 'Use'
11
11
 
12
+ SINGLE_SPACE_REGEXP = /[ \t]/.freeze
13
+
12
14
  private
13
15
 
14
16
  def side_space_range(range:, side:)
@@ -18,11 +20,11 @@ module RuboCop
18
20
  begin_pos = range.begin_pos
19
21
  end_pos = range.end_pos
20
22
  if side == :left
23
+ end_pos = begin_pos
21
24
  begin_pos = reposition(src, begin_pos, -1)
22
- end_pos -= 1
23
25
  end
24
26
  if side == :right
25
- begin_pos += 1
27
+ begin_pos = end_pos
26
28
  end_pos = reposition(src, end_pos, 1)
27
29
  end
28
30
  Parser::Source::Range.new(buffer, begin_pos, end_pos)
@@ -85,15 +87,15 @@ module RuboCop
85
87
  return false unless token
86
88
 
87
89
  if side == :left
88
- String(token.space_after?) == ' '
90
+ String(token.space_after?) =~ SINGLE_SPACE_REGEXP
89
91
  else
90
- String(token.space_before?) == ' '
92
+ String(token.space_before?) =~ SINGLE_SPACE_REGEXP
91
93
  end
92
94
  end
93
95
 
94
96
  def reposition(src, pos, step)
95
97
  offset = step == -1 ? -1 : 0
96
- pos += step while src[pos + offset] =~ /[ \t]/
98
+ pos += step while src[pos + offset] =~ SINGLE_SPACE_REGEXP
97
99
  pos.negative? ? 0 : pos
98
100
  end
99
101
 
@@ -18,12 +18,7 @@ module RuboCop
18
18
 
19
19
  def check(node, items, kind, begin_pos, end_pos)
20
20
  after_last_item = range_between(begin_pos, end_pos)
21
-
22
- # If there is any heredoc in items, then match the comma succeeding
23
- # any whitespace (except newlines), otherwise allow for newlines
24
- comma_regex = any_heredoc?(items) ? /\A[^\S\n]*,/ : /\A\s*,/
25
- comma_offset = after_last_item.source =~ comma_regex &&
26
- after_last_item.source.index(',')
21
+ comma_offset = comma_offset(items, after_last_item)
27
22
 
28
23
  if comma_offset && !inside_comment?(after_last_item, comma_offset)
29
24
  check_comma(node, kind, after_last_item.begin_pos + comma_offset)
@@ -32,6 +27,13 @@ module RuboCop
32
27
  end
33
28
  end
34
29
 
30
+ def comma_offset(items, range)
31
+ # If there is any heredoc in items, then match the comma succeeding
32
+ # any whitespace (except newlines), otherwise allow for newlines
33
+ comma_regex = any_heredoc?(items) ? /\A[^\S\n]*,/ : /\A\s*,/
34
+ range.source =~ comma_regex && range.source.index(',')
35
+ end
36
+
35
37
  def check_comma(node, kind, comma_pos)
36
38
  return if should_have_comma?(style, node)
37
39
 
@@ -20,7 +20,7 @@ module RuboCop
20
20
  OP_LIKE_METHODS = %i[eql? equal?].freeze
21
21
  BLACKLISTED = %i[+@ -@ [] []= << === `].freeze
22
22
 
23
- def_node_matcher :op_method_candidate?, <<-PATTERN
23
+ def_node_matcher :op_method_candidate?, <<~PATTERN
24
24
  (def [#op_method? $_] (args $(arg [!:other !:_other])) _)
25
25
  PATTERN
26
26
 
@@ -23,7 +23,7 @@ module RuboCop
23
23
  # than just standard ASCII characters
24
24
  SNAKE_CASE = /^[[:digit:][:upper:]_]+$/.freeze
25
25
 
26
- def_node_matcher :class_or_struct_return_method?, <<-PATTERN
26
+ def_node_matcher :class_or_struct_return_method?, <<~PATTERN
27
27
  (send
28
28
  (const _ {:Class :Struct}) :new
29
29
  ...)
@@ -63,7 +63,7 @@ module RuboCop
63
63
  (node.receiver.nil? || !literal_receiver?(node))
64
64
  end
65
65
 
66
- def_node_matcher :literal_receiver?, <<-PATTERN
66
+ def_node_matcher :literal_receiver?, <<~PATTERN
67
67
  {(send literal? ...)
68
68
  (send (begin literal?) ...)}
69
69
  PATTERN
@@ -50,14 +50,11 @@ module RuboCop
50
50
  def for_bad_filename(file_path)
51
51
  basename = File.basename(file_path)
52
52
  msg = if filename_good?(basename)
53
- return unless expect_matching_definition?
54
- return if find_class_or_module(processed_source.ast,
55
- to_namespace(file_path))
53
+ return if matching_definition?(file_path)
56
54
 
57
55
  no_definition_message(basename, file_path)
58
56
  else
59
- return if ignore_executable_scripts? &&
60
- processed_source.start_with?('#!')
57
+ return if bad_filename_allowed?
61
58
 
62
59
  other_message(basename)
63
60
  end
@@ -65,6 +62,16 @@ module RuboCop
65
62
  yield source_range(processed_source.buffer, 1, 0), msg
66
63
  end
67
64
 
65
+ def matching_definition?(file_path)
66
+ return true unless expect_matching_definition?
67
+
68
+ find_class_or_module(processed_source.ast, to_namespace(file_path))
69
+ end
70
+
71
+ def bad_filename_allowed?
72
+ ignore_executable_scripts? && processed_source.start_with?('#!')
73
+ end
74
+
68
75
  def no_definition_message(basename, file_path)
69
76
  format(MSG_NO_DEFINITION,
70
77
  basename: basename,
@@ -6,6 +6,15 @@ module RuboCop
6
6
  # This cop makes sure that all methods use the configured style,
7
7
  # snake_case or camelCase, for their names.
8
8
  #
9
+ # This cop has `IgnoredPatterns` configuration option.
10
+ #
11
+ # Naming/MethodName:
12
+ # IgnoredPatterns:
13
+ # - '\A\s*onSelectionBulkChange\s*'
14
+ # - '\A\s*onSelectionCleared\s*'
15
+ #
16
+ # Method names matching patterns are always allowed.
17
+ #
9
18
  # @example EnforcedStyle: snake_case (default)
10
19
  # # bad
11
20
  # def fooBar; end
@@ -21,11 +30,13 @@ module RuboCop
21
30
  # def fooBar; end
22
31
  class MethodName < Cop
23
32
  include ConfigurableNaming
33
+ include IgnoredPattern
24
34
 
25
35
  MSG = 'Use %<style>s for method names.'
26
36
 
27
37
  def on_def(node)
28
- return if node.operator_method?
38
+ return if node.operator_method? ||
39
+ matches_ignored_pattern?(node.method_name)
29
40
 
30
41
  check_name(node, node.method_name, node.loc.name)
31
42
  end