rubocop 0.9.1 → 0.10.0

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of rubocop might be problematic. Click here for more details.

Files changed (149) hide show
  1. data/.travis.yml +3 -1
  2. data/CHANGELOG.md +38 -0
  3. data/README.md +34 -0
  4. data/Rakefile +3 -0
  5. data/config/default.yml +14 -1
  6. data/config/enabled.yml +30 -7
  7. data/lib/rubocop.rb +15 -0
  8. data/lib/rubocop/cli.rb +48 -154
  9. data/lib/rubocop/config.rb +19 -22
  10. data/lib/rubocop/config_store.rb +2 -4
  11. data/lib/rubocop/cop/commissioner.rb +90 -0
  12. data/lib/rubocop/cop/cop.rb +38 -31
  13. data/lib/rubocop/cop/corrector.rb +84 -0
  14. data/lib/rubocop/cop/lint/assignment_in_condition.rb +0 -3
  15. data/lib/rubocop/cop/lint/block_alignment.rb +151 -0
  16. data/lib/rubocop/cop/lint/empty_ensure.rb +18 -0
  17. data/lib/rubocop/cop/lint/end_alignment.rb +0 -124
  18. data/lib/rubocop/cop/lint/end_in_method.rb +0 -2
  19. data/lib/rubocop/cop/lint/ensure_return.rb +3 -3
  20. data/lib/rubocop/cop/lint/eval.rb +0 -2
  21. data/lib/rubocop/cop/lint/handle_exceptions.rb +0 -2
  22. data/lib/rubocop/cop/lint/literal_in_condition.rb +0 -10
  23. data/lib/rubocop/cop/lint/loop.rb +0 -2
  24. data/lib/rubocop/cop/lint/rescue_exception.rb +0 -2
  25. data/lib/rubocop/cop/lint/shadowing_outer_local_variable.rb +2 -2
  26. data/lib/rubocop/cop/lint/unreachable_code.rb +0 -2
  27. data/lib/rubocop/cop/lint/unused_local_variable.rb +2 -2
  28. data/lib/rubocop/cop/lint/void.rb +0 -2
  29. data/lib/rubocop/cop/offence.rb +9 -0
  30. data/lib/rubocop/cop/rails/validation.rb +2 -1
  31. data/lib/rubocop/cop/style/access_control.rb +4 -3
  32. data/lib/rubocop/cop/style/alias.rb +2 -4
  33. data/lib/rubocop/cop/style/align_parameters.rb +0 -2
  34. data/lib/rubocop/cop/style/and_or.rb +4 -6
  35. data/lib/rubocop/cop/style/ascii_comments.rb +2 -2
  36. data/lib/rubocop/cop/style/ascii_identifiers.rb +2 -2
  37. data/lib/rubocop/cop/style/attr.rb +0 -2
  38. data/lib/rubocop/cop/style/avoid_class_vars.rb +0 -1
  39. data/lib/rubocop/cop/style/avoid_for.rb +0 -2
  40. data/lib/rubocop/cop/style/avoid_global_vars.rb +3 -7
  41. data/lib/rubocop/cop/style/avoid_perl_backrefs.rb +0 -2
  42. data/lib/rubocop/cop/style/avoid_perlisms.rb +2 -4
  43. data/lib/rubocop/cop/style/begin_block.rb +0 -2
  44. data/lib/rubocop/cop/style/block_comments.rb +2 -2
  45. data/lib/rubocop/cop/style/block_nesting.rb +3 -3
  46. data/lib/rubocop/cop/style/blocks.rb +0 -2
  47. data/lib/rubocop/cop/style/case_equality.rb +0 -2
  48. data/lib/rubocop/cop/style/case_indentation.rb +0 -2
  49. data/lib/rubocop/cop/style/character_literal.rb +10 -6
  50. data/lib/rubocop/cop/style/class_and_module_camel_case.rb +0 -4
  51. data/lib/rubocop/cop/style/class_methods.rb +1 -1
  52. data/lib/rubocop/cop/style/collection_methods.rb +3 -5
  53. data/lib/rubocop/cop/style/colon_method_call.rb +3 -3
  54. data/lib/rubocop/cop/style/comment_annotation.rb +44 -0
  55. data/lib/rubocop/cop/style/constant_name.rb +0 -2
  56. data/lib/rubocop/cop/style/def_parentheses.rb +0 -8
  57. data/lib/rubocop/cop/style/documentation.rb +6 -2
  58. data/lib/rubocop/cop/style/dot_position.rb +0 -2
  59. data/lib/rubocop/cop/style/empty_line_between_defs.rb +0 -2
  60. data/lib/rubocop/cop/style/empty_lines.rb +10 -8
  61. data/lib/rubocop/cop/style/empty_literal.rb +3 -1
  62. data/lib/rubocop/cop/style/encoding.rb +7 -6
  63. data/lib/rubocop/cop/style/end_block.rb +0 -2
  64. data/lib/rubocop/cop/style/end_of_line.rb +4 -3
  65. data/lib/rubocop/cop/style/favor_join.rb +0 -2
  66. data/lib/rubocop/cop/style/favor_modifier.rb +9 -9
  67. data/lib/rubocop/cop/style/favor_sprintf.rb +0 -2
  68. data/lib/rubocop/cop/style/favor_unless_over_negated_if.rb +0 -2
  69. data/lib/rubocop/cop/style/hash_syntax.rb +0 -2
  70. data/lib/rubocop/cop/style/if_then_else.rb +0 -2
  71. data/lib/rubocop/cop/style/lambda.rb +0 -2
  72. data/lib/rubocop/cop/style/leading_comment_space.rb +2 -2
  73. data/lib/rubocop/cop/style/line_continuation.rb +4 -3
  74. data/lib/rubocop/cop/style/line_length.rb +4 -3
  75. data/lib/rubocop/cop/style/method_and_variable_snake_case.rb +4 -3
  76. data/lib/rubocop/cop/style/method_call_parentheses.rb +0 -2
  77. data/lib/rubocop/cop/style/method_length.rb +0 -4
  78. data/lib/rubocop/cop/style/not.rb +0 -2
  79. data/lib/rubocop/cop/style/op_method.rb +0 -2
  80. data/lib/rubocop/cop/style/parameter_lists.rb +0 -2
  81. data/lib/rubocop/cop/style/parentheses_around_condition.rb +12 -6
  82. data/lib/rubocop/cop/style/proc.rb +0 -2
  83. data/lib/rubocop/cop/style/reduce_arguments.rb +0 -2
  84. data/lib/rubocop/cop/style/redundant_begin.rb +45 -0
  85. data/lib/rubocop/cop/style/redundant_return.rb +59 -0
  86. data/lib/rubocop/cop/style/redundant_self.rb +83 -0
  87. data/lib/rubocop/cop/style/regexp_literal.rb +0 -2
  88. data/lib/rubocop/cop/style/rescue_modifier.rb +13 -21
  89. data/lib/rubocop/cop/style/semicolon.rb +15 -9
  90. data/lib/rubocop/cop/style/single_line_methods.rb +0 -4
  91. data/lib/rubocop/cop/style/space_after_comma_etc.rb +2 -2
  92. data/lib/rubocop/cop/style/space_after_control_keyword.rb +0 -1
  93. data/lib/rubocop/cop/style/string_literals.rb +5 -2
  94. data/lib/rubocop/cop/style/surrounding_space.rb +106 -91
  95. data/lib/rubocop/cop/style/tab.rb +4 -3
  96. data/lib/rubocop/cop/style/ternary_operator.rb +0 -4
  97. data/lib/rubocop/cop/style/trailing_whitespace.rb +4 -3
  98. data/lib/rubocop/cop/style/trivial_accessors.rb +51 -6
  99. data/lib/rubocop/cop/style/unless_else.rb +0 -2
  100. data/lib/rubocop/cop/style/variable_interpolation.rb +0 -2
  101. data/lib/rubocop/cop/style/when_then.rb +3 -3
  102. data/lib/rubocop/cop/style/while_until_do.rb +3 -5
  103. data/lib/rubocop/cop/style/word_array.rb +0 -2
  104. data/lib/rubocop/cop/util.rb +0 -4
  105. data/lib/rubocop/formatter/file_list_formatter.rb +18 -0
  106. data/lib/rubocop/formatter/formatter_set.rb +2 -1
  107. data/lib/rubocop/processed_source.rb +27 -0
  108. data/lib/rubocop/rake_task.rb +50 -0
  109. data/lib/rubocop/source_parser.rb +105 -0
  110. data/lib/rubocop/target_finder.rb +67 -0
  111. data/lib/rubocop/token.rb +22 -0
  112. data/lib/rubocop/version.rb +1 -1
  113. data/rubocop.gemspec +5 -3
  114. data/spec/project_spec.rb +0 -11
  115. data/spec/rubocop/cli_spec.rb +112 -6
  116. data/spec/rubocop/config_spec.rb +13 -17
  117. data/spec/rubocop/config_store_spec.rb +8 -23
  118. data/spec/rubocop/cops/commissioner_spec.rb +72 -0
  119. data/spec/rubocop/cops/corrector_spec.rb +63 -0
  120. data/spec/rubocop/cops/lint/assignment_in_condition_spec.rb +2 -2
  121. data/spec/rubocop/cops/lint/block_alignment_spec.rb +357 -0
  122. data/spec/rubocop/cops/lint/empty_ensure_spec.rb +33 -0
  123. data/spec/rubocop/cops/lint/end_alignment_spec.rb +0 -263
  124. data/spec/rubocop/cops/lint/ensure_return_spec.rb +6 -9
  125. data/spec/rubocop/cops/offence_spec.rb +28 -0
  126. data/spec/rubocop/cops/style/and_or_spec.rb +21 -11
  127. data/spec/rubocop/cops/style/ascii_identifiers_spec.rb +14 -0
  128. data/spec/rubocop/cops/style/avoid_global_vars_spec.rb +10 -14
  129. data/spec/rubocop/cops/style/character_literal_spec.rb +17 -2
  130. data/spec/rubocop/cops/style/colon_method_call_spec.rb +20 -15
  131. data/spec/rubocop/cops/style/comment_annotation_spec.rb +62 -0
  132. data/spec/rubocop/cops/style/encoding_spec.rb +7 -0
  133. data/spec/rubocop/cops/style/parentheses_around_condition_spec.rb +37 -9
  134. data/spec/rubocop/cops/style/redundant_begin_spec.rb +63 -0
  135. data/spec/rubocop/cops/style/redundant_return_spec.rb +64 -0
  136. data/spec/rubocop/cops/style/redundant_self_spec.rb +76 -0
  137. data/spec/rubocop/cops/style/string_literals_spec.rb +18 -13
  138. data/spec/rubocop/cops/style/trivial_accessors_spec.rb +110 -52
  139. data/spec/rubocop/cops/style/when_then_spec.rb +14 -7
  140. data/spec/rubocop/cops/style/while_until_do_spec.rb +12 -0
  141. data/spec/rubocop/cops/variable_inspector_spec.rb +3 -5
  142. data/spec/rubocop/formatter/file_list_formatter_spec.rb +33 -0
  143. data/spec/rubocop/processed_source_spec.rb +67 -0
  144. data/spec/rubocop/source_parser_spec.rb +141 -0
  145. data/spec/rubocop/target_finder_spec.rb +180 -0
  146. data/spec/rubocop/token_spec.rb +27 -0
  147. data/spec/spec_helper.rb +24 -4
  148. metadata +108 -18
  149. checksums.yaml +0 -7
@@ -0,0 +1,83 @@
1
+ # encoding: utf-8
2
+
3
+ module Rubocop
4
+ module Cop
5
+ module Style
6
+ # This cop checks for redundant uses of `self`. It is only needed when
7
+ # calling a write accessor on self.
8
+ #
9
+ # Special cases:
10
+ #
11
+ # We allow uses of `self` with operators because it would be awkward
12
+ # otherwise.
13
+ class RedundantSelf < Cop
14
+ MSG = 'Redundant `self` detected.'
15
+
16
+ def initialize
17
+ super
18
+ @allowed_send_nodes = []
19
+ @local_variables = []
20
+ end
21
+
22
+ # Assignment of self.x
23
+
24
+ def on_or_asgn(node)
25
+ lhs, _rhs = *node
26
+ allow_self(lhs)
27
+ end
28
+
29
+ alias_method :on_and_asgn, :on_or_asgn
30
+
31
+ def on_op_asgn(node)
32
+ lhs, _op, _rhs = *node
33
+ allow_self(lhs)
34
+ end
35
+
36
+ # Using self.x to distinguish from local variable x
37
+
38
+ def on_def(node)
39
+ @local_variables = []
40
+ end
41
+
42
+ def on_defs(node)
43
+ @local_variables = []
44
+ end
45
+
46
+ def on_lvasgn(node)
47
+ lhs, _rhs = *node
48
+ @local_variables << lhs
49
+ end
50
+
51
+ # Detect offences
52
+
53
+ def on_send(node)
54
+ receiver, method_name, *_args = *node
55
+ if receiver && receiver.type == :self
56
+ unless operator?(method_name) || keyword?(method_name) ||
57
+ @allowed_send_nodes.include?(node) ||
58
+ @local_variables.include?(method_name)
59
+ add_offence(:convention, receiver.loc.expression, MSG)
60
+ end
61
+ end
62
+ end
63
+
64
+ private
65
+
66
+ def operator?(method_name)
67
+ method_name.to_s =~ /\W/
68
+ end
69
+
70
+ def keyword?(method_name)
71
+ [:class, :for].include?(method_name)
72
+ end
73
+
74
+ def allow_self(node)
75
+ if node.type == :send
76
+ receiver, _method_name, *_args = *node
77
+ @allowed_send_nodes << node if receiver && receiver.type == :self
78
+ end
79
+ end
80
+ end
81
+ end
82
+ end
83
+ end
@@ -16,8 +16,6 @@ module Rubocop
16
16
  error_message('only ') if slashes <= max
17
17
  end
18
18
  add_offence(:convention, node.loc.expression, msg) if msg
19
-
20
- super
21
19
  end
22
20
 
23
21
  def self.max_slashes
@@ -7,48 +7,40 @@ module Rubocop
7
7
  class RescueModifier < Cop
8
8
  MSG = 'Avoid using rescue in its modifier form.'
9
9
 
10
+ def on_rescue(node)
11
+ return if ignored_node?(node)
12
+
13
+ add_offence(:convention, node.loc.expression, MSG)
14
+ end
15
+
10
16
  def on_kwbegin(node)
11
17
  body, *_ = *node
12
- return if normal_rescue?(body)
13
- super
18
+ check_rescue(body)
14
19
  end
15
20
 
16
21
  def on_def(node)
17
22
  _method_name, _args, body = *node
18
- return if normal_rescue?(body)
19
- super
23
+ check_rescue(body)
20
24
  end
21
25
 
22
26
  def on_defs(node)
23
27
  _receiver, _method_name, _args, body = *node
24
- return if normal_rescue?(body)
25
- super
28
+ check_rescue(body)
26
29
  end
27
30
 
28
- def normal_rescue?(node)
29
- return false unless node
31
+ def check_rescue(node)
32
+ return unless node
30
33
 
31
34
  case node.type
32
35
  when :rescue
33
- # Skip only the rescue node and continue processing its children.
34
- process_regular_node(node)
35
- true
36
+ ignore_node(node)
36
37
  when :ensure
37
38
  first_child = node.children.first
38
39
  if first_child && first_child.type == :rescue
39
- process_regular_node(first_child)
40
- true
41
- else
42
- false
40
+ ignore_node(first_child)
43
41
  end
44
- else
45
- false
46
42
  end
47
43
  end
48
-
49
- def on_rescue(node)
50
- add_offence(:convention, node.loc.expression, MSG)
51
- end
52
44
  end
53
45
  end
54
46
  end
@@ -8,10 +8,10 @@ module Rubocop
8
8
  class Semicolon < Cop
9
9
  MSG = 'Do not use semicolons to terminate expressions.'
10
10
 
11
- def inspect(source_buffer, source, tokens, ast, comments)
12
- return unless ast
11
+ def investigate(processed_source)
12
+ return unless processed_source.ast
13
13
 
14
- on_node(:begin, ast) do |node|
14
+ on_node(:begin, processed_source.ast) do |node|
15
15
  exprs = node.children
16
16
 
17
17
  next if exprs.size < 2
@@ -26,20 +26,26 @@ module Rubocop
26
26
  # TODO: Find the correct position of the semicolon. We don't
27
27
  # know if the first semicolon on the line is a separator of
28
28
  # expressions. It's just a guess.
29
- column = source[line - 1].index(';')
29
+ column = processed_source[line - 1].index(';')
30
30
  add_offence(:convention,
31
- source_range(source_buffer, source[0...(line - 1)],
31
+ source_range(processed_source.buffer,
32
+ processed_source[0...(line - 1)],
32
33
  column, 1),
33
34
  MSG)
34
35
  end
35
36
  end
36
37
  end
37
38
 
38
- tokens.group_by { |t| t.pos.line }.each do |line, line_tokens|
39
- if line_tokens.last.type == :tSEMI # rubocop:disable SymbolName
40
- column = line_tokens.last.pos.column
39
+ tokens_for_lines = processed_source.tokens.group_by do |token|
40
+ token.pos.line
41
+ end
42
+
43
+ tokens_for_lines.each do |line, tokens|
44
+ if tokens.last.type == :tSEMI # rubocop:disable SymbolName
45
+ column = tokens.last.pos.column
41
46
  add_offence(:convention,
42
- source_range(source_buffer, source[0...(line - 1)],
47
+ source_range(processed_source.buffer,
48
+ processed_source[0...(line - 1)],
43
49
  column, 1),
44
50
  MSG)
45
51
  end
@@ -14,14 +14,10 @@ module Rubocop
14
14
 
15
15
  def on_def(node)
16
16
  check(node)
17
-
18
- super
19
17
  end
20
18
 
21
19
  def on_defs(node)
22
20
  check(node)
23
-
24
- super
25
21
  end
26
22
 
27
23
  private
@@ -10,8 +10,8 @@ module Rubocop
10
10
  module SpaceAfterCommaEtc
11
11
  MSG = 'Space missing after %s.'
12
12
 
13
- def inspect(source_buffer, source, tokens, ast, comments)
14
- tokens.each_cons(2) do |t1, t2|
13
+ def investigate(processed_source)
14
+ processed_source.tokens.each_cons(2) do |t1, t2|
15
15
  if kind(t1) && t1.pos.line == t2.pos.line &&
16
16
  t2.pos.column == t1.pos.column + offset(t1)
17
17
  add_offence(:convention, t1.pos, sprintf(MSG, kind(t1)))
@@ -23,7 +23,6 @@ module Rubocop
23
23
  KEYWORDS.each do |keyword|
24
24
  define_method(:"on_#{keyword}") do |node|
25
25
  on_keyword(node)
26
- super(node)
27
26
  end
28
27
  end
29
28
  end
@@ -12,6 +12,7 @@ module Rubocop
12
12
  # Constants like __FILE__ are handled as strings,
13
13
  # but don't respond to begin.
14
14
  return unless node.loc.respond_to?(:begin)
15
+ return if part_of_ignored_node?(node)
15
16
 
16
17
  # regex matches IF there is a ' or there is a \\ in the string that
17
18
  # is not preceeded/followed by another \\ (e.g. "\\x34") but not
@@ -27,8 +28,10 @@ module Rubocop
27
28
  alias_method :on_regexp, :ignore_node
28
29
 
29
30
  def autocorrect_action(node)
30
- replace(node.loc.begin, "'")
31
- replace(node.loc.end, "'")
31
+ @corrections << lambda do |corrector|
32
+ corrector.replace(node.loc.begin, "'")
33
+ corrector.replace(node.loc.end, "'")
34
+ end
32
35
  end
33
36
  end
34
37
  end
@@ -9,36 +9,36 @@ module Rubocop
9
9
  module SurroundingSpace
10
10
  def space_between?(t1, t2)
11
11
  char_preceding_2nd_token =
12
- @source[t2.pos.line - 1][t2.pos.column - 1]
12
+ @processed_source[t2.pos.line - 1][t2.pos.column - 1]
13
13
  if char_preceding_2nd_token == '+' && t1.type != :tPLUS
14
14
  # Special case. A unary plus is not present in the tokens.
15
15
  char_preceding_2nd_token =
16
- @source[t2.pos.line - 1][t2.pos.column - 2]
16
+ @processed_source[t2.pos.line - 1][t2.pos.column - 2]
17
17
  end
18
18
  t2.pos.line > t1.pos.line || char_preceding_2nd_token == ' '
19
19
  end
20
20
 
21
- def index_of_first_token(node, tokens)
22
- @token_table ||= build_token_table(tokens)
21
+ def index_of_first_token(node)
23
22
  b = node.loc.expression.begin
24
- @token_table[[b.line, b.column]]
23
+ token_table[[b.line, b.column]]
25
24
  end
26
25
 
27
- def index_of_last_token(node, tokens)
28
- @token_table ||= build_token_table(tokens)
26
+ def index_of_last_token(node)
29
27
  e = node.loc.expression.end
30
28
  (0...e.column).to_a.reverse.find do |c|
31
- ix = @token_table[[e.line, c]]
29
+ ix = token_table[[e.line, c]]
32
30
  return ix if ix
33
31
  end
34
32
  end
35
33
 
36
- def build_token_table(tokens)
37
- table = {}
38
- tokens.each_with_index do |t, ix|
39
- table[[t.pos.line, t.pos.column]] = ix
34
+ def token_table
35
+ @token_table ||= begin
36
+ table = {}
37
+ @processed_source.tokens.each_with_index do |t, ix|
38
+ table[[t.pos.line, t.pos.column]] = ix
39
+ end
40
+ table
40
41
  end
41
- table
42
42
  end
43
43
  end
44
44
 
@@ -55,12 +55,10 @@ module Rubocop
55
55
  :tNMATCH, :tEQ, :tNEQ, :tGT, :tRSHFT, :tGEQ, :tLT,
56
56
  :tLSHFT, :tLEQ, :tASSOC, :tEQQ, :tCMP, :tOP_ASGN]
57
57
 
58
- def inspect(source_buffer, source, tokens, sexp, comments)
59
- return unless sexp
60
-
61
- @source = source
62
- positions_not_to_check = get_positions_not_to_check(tokens, sexp)
63
-
58
+ def investigate(processed_source)
59
+ return unless processed_source.ast
60
+ @processed_source = processed_source
61
+ tokens = processed_source.tokens
64
62
  tokens.each_cons(3) do |token_before, token, token_after|
65
63
  next if token_before.type == :kDEF # TODO: remove?
66
64
  next if token_before.type == :tDOT # Called as method.
@@ -80,77 +78,87 @@ module Rubocop
80
78
  # Returns an array of positions marking the tokens that this cop
81
79
  # should not check, either because the token is not an operator
82
80
  # or because another cop does the check.
83
- def get_positions_not_to_check(tokens, sexp)
84
- positions_not_to_check = []
85
- do_not_check_block_arg_pipes(sexp, positions_not_to_check)
86
- do_not_check_param_default(tokens, sexp, positions_not_to_check)
87
- do_not_check_class_lshift_self(tokens, sexp, positions_not_to_check)
88
- do_not_check_def_things(tokens, sexp, positions_not_to_check)
89
- do_not_check_singleton_operator_defs(tokens, sexp,
90
- positions_not_to_check)
91
- positions_not_to_check
81
+ def positions_not_to_check
82
+ @positions_not_to_check ||= begin
83
+ positions = []
84
+ positions.concat(do_not_check_block_arg_pipes)
85
+ positions.concat(do_not_check_param_default)
86
+ positions.concat(do_not_check_class_lshift_self)
87
+ positions.concat(do_not_check_def_things)
88
+ positions.concat(do_not_check_singleton_operator_defs)
89
+ positions
90
+ end
92
91
  end
93
92
 
94
- def do_not_check_block_arg_pipes(sexp, positions_not_to_check)
93
+ def do_not_check_block_arg_pipes
95
94
  # each { |a| }
96
95
  # ^ ^
97
- on_node(:block, sexp) do |b|
96
+ positions = []
97
+ on_node(:block, @processed_source.ast) do |b|
98
98
  on_node(:args, b) do |a|
99
- positions_not_to_check << a.loc.begin << a.loc.end if a.loc.begin
99
+ positions << a.loc.begin << a.loc.end if a.loc.begin
100
100
  end
101
101
  end
102
+ positions
102
103
  end
103
104
 
104
- def do_not_check_param_default(tokens, sexp, positions_not_to_check)
105
+ def do_not_check_param_default
105
106
  # func(a, b=nil)
106
107
  # ^
107
- on_node(:optarg, sexp) do |optarg|
108
- _arg, equals, _value = tokens[index_of_first_token(optarg, tokens),
108
+ positions = []
109
+ tokens = @processed_source.tokens
110
+ on_node(:optarg, @processed_source.ast) do |optarg|
111
+ _arg, equals, _value = tokens[index_of_first_token(optarg),
109
112
  3]
110
- positions_not_to_check << equals.pos
113
+ positions << equals.pos
111
114
  end
115
+ positions
112
116
  end
113
117
 
114
- def do_not_check_class_lshift_self(tokens,
115
- sexp,
116
- positions_not_to_check)
118
+ def do_not_check_class_lshift_self
117
119
  # class <<self
118
120
  # ^
119
- on_node(:sclass, sexp) do |sclass|
120
- ix = index_of_first_token(sclass, tokens)
121
+ positions = []
122
+ tokens = @processed_source.tokens
123
+ on_node(:sclass, @processed_source.ast) do |sclass|
124
+ ix = index_of_first_token(sclass)
121
125
  if tokens[ix, 2].map(&:type) == [:kCLASS, :tLSHFT]
122
- positions_not_to_check << tokens[ix + 1].pos
126
+ positions << tokens[ix + 1].pos
123
127
  end
124
128
  end
129
+ positions
125
130
  end
126
131
 
127
- def do_not_check_def_things(tokens, sexp, positions_not_to_check)
132
+ def do_not_check_def_things
128
133
  # def +(other)
129
134
  # ^
130
- on_node(:def, sexp) do |def_node|
135
+ positions = []
136
+ tokens = @processed_source.tokens
137
+ on_node(:def, @processed_source.ast) do |def_node|
131
138
  # def each &block
132
139
  # ^
133
140
  # def each *args
134
141
  # ^
135
142
  on_node([:blockarg, :restarg], def_node) do |arg_node|
136
- positions_not_to_check <<
137
- tokens[index_of_first_token(arg_node, tokens)].pos
143
+ positions << tokens[index_of_first_token(arg_node)].pos
138
144
  end
139
- positions_not_to_check <<
140
- tokens[index_of_first_token(def_node, tokens) + 1].pos
145
+ positions << tokens[index_of_first_token(def_node) + 1].pos
141
146
  end
147
+ positions
142
148
  end
143
149
 
144
- def do_not_check_singleton_operator_defs(tokens, sexp,
145
- positions_not_to_check)
150
+ def do_not_check_singleton_operator_defs
146
151
  # def self.===(other)
147
152
  # ^
148
- on_node(:defs, sexp) do |defs_node|
153
+ positions = []
154
+ tokens = @processed_source.tokens
155
+ on_node(:defs, @processed_source.ast) do |defs_node|
149
156
  _receiver, name, _args = *defs_node
150
- ix = index_of_first_token(defs_node, tokens)
157
+ ix = index_of_first_token(defs_node)
151
158
  name_token = tokens[ix..-1].find { |t| t.text == name.to_s }
152
- positions_not_to_check << name_token.pos
159
+ positions << name_token.pos
153
160
  end
161
+ positions
154
162
  end
155
163
 
156
164
  def check_missing_space(token_before, token, token_after)
@@ -172,11 +180,11 @@ module Rubocop
172
180
  MSG_LEFT = "Surrounding space missing for '{'."
173
181
  MSG_RIGHT = "Space missing to the left of '}'."
174
182
 
175
- def inspect(source_buffer, source, tokens, sexp, comments)
176
- return unless sexp
177
- @source = source
178
- positions_not_to_check = get_positions_not_to_check(tokens, sexp)
179
- tokens.each_cons(2) do |t1, t2|
183
+ def investigate(processed_source)
184
+ return unless processed_source.ast
185
+ @processed_source = processed_source
186
+
187
+ processed_source.tokens.each_cons(2) do |t1, t2|
180
188
  next if ([t1.pos, t2.pos] - positions_not_to_check).size < 2
181
189
 
182
190
  type1, type2 = t1.type, t2.type
@@ -187,25 +195,30 @@ module Rubocop
187
195
  end
188
196
  end
189
197
 
190
- def get_positions_not_to_check(tokens, sexp)
191
- positions_not_to_check = []
198
+ def positions_not_to_check
199
+ @positions_not_to_check ||= begin
200
+ positions = []
201
+ ast = @processed_source.ast
202
+ tokens = @processed_source.tokens
192
203
 
193
- on_node(:hash, sexp) do |hash|
194
- b_ix = index_of_first_token(hash, tokens)
195
- e_ix = index_of_last_token(hash, tokens)
196
- positions_not_to_check << tokens[b_ix].pos << tokens[e_ix].pos
197
- end
204
+ on_node(:hash, ast) do |hash|
205
+ b_ix = index_of_first_token(hash)
206
+ e_ix = index_of_last_token(hash)
207
+ positions << tokens[b_ix].pos << tokens[e_ix].pos
208
+ end
198
209
 
199
- # TODO: Check braces inside string/symbol/regexp/xstr interpolation.
200
- on_node([:dstr, :dsym, :regexp, :xstr], sexp) do |s|
201
- b_ix = index_of_first_token(s, tokens)
202
- e_ix = index_of_last_token(s, tokens)
203
- tokens[b_ix..e_ix].each do |t|
204
- positions_not_to_check << t.pos if t.type == :tRCURLY
210
+ # TODO: Check braces inside string/symbol/regexp/xstr
211
+ # interpolation.
212
+ on_node([:dstr, :dsym, :regexp, :xstr], ast) do |s|
213
+ b_ix = index_of_first_token(s)
214
+ e_ix = index_of_last_token(s)
215
+ tokens[b_ix..e_ix].each do |t|
216
+ positions << t.pos if t.type == :tRCURLY
217
+ end
205
218
  end
206
- end
207
219
 
208
- positions_not_to_check
220
+ positions
221
+ end
209
222
  end
210
223
 
211
224
  def check(t1, t2, msg)
@@ -222,16 +235,16 @@ module Rubocop
222
235
  include SurroundingSpace
223
236
  MSG = 'Space inside %s detected.'
224
237
 
225
- def inspect(source_buffer, source, tokens, sexp, comments)
226
- @source = source
238
+ def investigate(processed_source)
239
+ @processed_source = processed_source
227
240
  left, right, kind = specifics
228
- tokens.each_cons(2) do |t1, t2|
241
+ processed_source.tokens.each_cons(2) do |t1, t2|
229
242
  if t1.type == left || t2.type == right
230
243
  if t2.pos.line == t1.pos.line && space_between?(t1, t2)
231
- space_range = Parser::Source::Range.new(source_buffer,
232
- t1.pos.end_pos,
233
- t2.pos.begin_pos)
234
- add_offence(:convention, space_range, format(MSG, kind))
244
+ range = Parser::Source::Range.new(processed_source.buffer,
245
+ t1.pos.end_pos,
246
+ t2.pos.begin_pos)
247
+ add_offence(:convention, range, format(MSG, kind))
235
248
  end
236
249
  end
237
250
  end
@@ -262,12 +275,14 @@ module Rubocop
262
275
  include SurroundingSpace
263
276
  MSG = 'Space inside hash literal braces %s.'
264
277
 
265
- def inspect(source_buffer, source, tokens, sexp, comments)
266
- return unless sexp
267
- @source = source
268
- on_node(:hash, sexp) do |hash|
269
- b_ix = index_of_first_token(hash, tokens)
270
- e_ix = index_of_last_token(hash, tokens)
278
+ def investigate(processed_source)
279
+ return unless processed_source.ast
280
+ @processed_source = processed_source
281
+ tokens = processed_source.tokens
282
+
283
+ on_node(:hash, processed_source.ast) do |hash|
284
+ b_ix = index_of_first_token(hash)
285
+ e_ix = index_of_last_token(hash)
271
286
  if tokens[b_ix].type == :tLBRACE # Hash literal with braces?
272
287
  check(tokens[b_ix], tokens[b_ix + 1])
273
288
  check(tokens[e_ix - 1], tokens[e_ix])
@@ -297,12 +312,12 @@ module Rubocop
297
312
  include SurroundingSpace
298
313
  MSG = 'Surrounding space missing in default value assignment.'
299
314
 
300
- def inspect(source_buffer, source, tokens, sexp, comments)
301
- return unless sexp
302
- @source = source
303
- on_node(:optarg, sexp) do |optarg|
304
- index = index_of_first_token(optarg, tokens)
305
- arg, equals, value = tokens[index, 3]
315
+ def investigate(processed_source)
316
+ return unless processed_source.ast
317
+ @processed_source = processed_source
318
+ on_node(:optarg, processed_source.ast) do |optarg|
319
+ index = index_of_first_token(optarg)
320
+ arg, equals, value = processed_source.tokens[index, 3]
306
321
  unless space_between?(arg, equals) && space_between?(equals, value)
307
322
  add_offence(:convention, equals.pos, MSG)
308
323
  end