transpec 0.0.1 → 0.0.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (41) hide show
  1. checksums.yaml +4 -4
  2. data/.rubocop.yml +4 -0
  3. data/CHANGELOG.md +9 -0
  4. data/Guardfile +4 -0
  5. data/README.md +102 -5
  6. data/README.md.erb +107 -0
  7. data/Rakefile +26 -5
  8. data/bin/transpec +1 -1
  9. data/lib/transpec/ast/scanner.rb +3 -0
  10. data/lib/transpec/ast/scope_stack.rb +2 -0
  11. data/lib/transpec/cli.rb +4 -0
  12. data/lib/transpec/rewriter.rb +14 -2
  13. data/lib/transpec/syntax.rb +36 -1
  14. data/lib/transpec/syntax/any_instanceable.rb +24 -0
  15. data/lib/transpec/syntax/be_close.rb +32 -0
  16. data/lib/transpec/syntax/double.rb +14 -8
  17. data/lib/transpec/syntax/expectizable.rb +20 -0
  18. data/lib/transpec/syntax/matcher.rb +16 -8
  19. data/lib/transpec/syntax/method_stub.rb +26 -40
  20. data/lib/transpec/syntax/send_node_syntax.rb +2 -4
  21. data/lib/transpec/syntax/should.rb +25 -16
  22. data/lib/transpec/syntax/should_receive.rb +32 -35
  23. data/lib/transpec/version.rb +1 -1
  24. data/spec/spec_helper.rb +8 -6
  25. data/spec/support/shared_context.rb +4 -0
  26. data/spec/transpec/ast/scanner_spec.rb +1 -1
  27. data/spec/transpec/ast/scope_stack_spec.rb +1 -0
  28. data/spec/transpec/cli_spec.rb +1 -0
  29. data/spec/transpec/configuration_spec.rb +1 -0
  30. data/spec/transpec/git_spec.rb +8 -0
  31. data/spec/transpec/rewriter_spec.rb +30 -0
  32. data/spec/transpec/syntax/be_close_spec.rb +50 -0
  33. data/spec/transpec/syntax/double_spec.rb +3 -2
  34. data/spec/transpec/syntax/matcher_spec.rb +1 -0
  35. data/spec/transpec/syntax/method_stub_spec.rb +1 -0
  36. data/spec/transpec/syntax/should_receive_spec.rb +1 -0
  37. data/spec/transpec/syntax/should_spec.rb +1 -0
  38. data/spec/transpec/util_spec.rb +1 -0
  39. data/transpec.gemspec +1 -0
  40. metadata +23 -3
  41. data/lib/transpec.rb +0 -17
@@ -0,0 +1,24 @@
1
+ # coding: utf-8
2
+
3
+ require 'transpec/syntax/send_node_syntax'
4
+
5
+ module Transpec
6
+ class Syntax
7
+ module AnyInstanceable
8
+ include SendNodeSyntax
9
+
10
+ def any_instance?
11
+ !class_node_of_any_instance.nil?
12
+ end
13
+
14
+ def class_node_of_any_instance
15
+ return nil unless subject_node.type == :send
16
+ return nil unless subject_node.children.count == 2
17
+ receiver_node, method_name = *subject_node
18
+ return nil unless method_name == :any_instance
19
+ return nil unless receiver_node.type == :const
20
+ receiver_node
21
+ end
22
+ end
23
+ end
24
+ end
@@ -0,0 +1,32 @@
1
+ # coding: utf-8
2
+
3
+ require 'transpec/syntax'
4
+ require 'transpec/syntax/send_node_syntax'
5
+
6
+ module Transpec
7
+ class Syntax
8
+ class BeClose < Syntax
9
+ def convert_to_be_within!
10
+ _receiver_node, _method_name, expected_node, delta_node = *node
11
+
12
+ be_within_source = 'be_within('
13
+ be_within_source << delta_node.loc.expression.source
14
+ be_within_source << ').of('
15
+ be_within_source << expected_node.loc.expression.source
16
+ be_within_source << ')'
17
+
18
+ replace(expression_range, be_within_source)
19
+ end
20
+
21
+ private
22
+
23
+ def self.target_receiver_node?(node)
24
+ node.nil?
25
+ end
26
+
27
+ def self.target_method_names
28
+ [:be_close]
29
+ end
30
+ end
31
+ end
32
+ end
@@ -1,20 +1,26 @@
1
1
  # coding: utf-8
2
2
 
3
+ require 'transpec/syntax'
4
+ require 'transpec/syntax/send_node_syntax'
5
+
3
6
  module Transpec
4
7
  class Syntax
5
8
  class Double < Syntax
6
9
  include SendNodeSyntax
7
10
 
8
- def self.target_node?(node)
9
- return false unless node.type == :send
10
- receiver_node, method_name, *_ = *node
11
- return false if receiver_node
12
- [:double, :mock, :stub].include?(method_name)
11
+ def convert_to_double!
12
+ return if method_name == :double
13
+ replace(selector_range, 'double')
13
14
  end
14
15
 
15
- def replace_deprecated_method!
16
- return if method_name == :double
17
- @source_rewriter.replace(selector_range, 'double')
16
+ private
17
+
18
+ def self.target_receiver_node?(node)
19
+ node.nil?
20
+ end
21
+
22
+ def self.target_method_names
23
+ [:double, :mock, :stub]
18
24
  end
19
25
  end
20
26
  end
@@ -0,0 +1,20 @@
1
+ # coding: utf-8
2
+
3
+ require 'transpec/syntax/send_node_syntax'
4
+
5
+ module Transpec
6
+ class Syntax
7
+ module Expectizable
8
+ include SendNodeSyntax
9
+
10
+ def wrap_subject_in_expect!
11
+ if subject_range.source[0] == '('
12
+ insert_before(subject_range, 'expect')
13
+ else
14
+ insert_before(subject_range, 'expect(')
15
+ insert_after(subject_range, ')')
16
+ end
17
+ end
18
+ end
19
+ end
20
+ end
@@ -1,10 +1,18 @@
1
1
  # coding: utf-8
2
2
 
3
+ require 'transpec/syntax'
4
+ require 'transpec/syntax/send_node_syntax'
5
+ require 'transpec/util'
6
+
3
7
  module Transpec
4
8
  class Syntax
5
9
  class Matcher < Syntax
6
10
  include SendNodeSyntax, Util
7
11
 
12
+ def self.target_node?(node)
13
+ false
14
+ end
15
+
8
16
  def initialize(node, in_example_group_context, source_rewriter)
9
17
  @node = node
10
18
  @in_example_group_context = in_example_group_context
@@ -14,15 +22,15 @@ module Transpec
14
22
  def correct_operator!(parenthesize_arg = true)
15
23
  case method_name
16
24
  when :==
17
- @source_rewriter.replace(selector_range, 'eq')
25
+ replace(selector_range, 'eq')
18
26
  parenthesize!(parenthesize_arg)
19
27
  when :===, :<, :<=, :>, :>=
20
- @source_rewriter.insert_before(selector_range, 'be ')
28
+ insert_before(selector_range, 'be ')
21
29
  when :=~
22
30
  if arg_node.type == :array
23
- @source_rewriter.replace(selector_range, 'match_array')
31
+ replace(selector_range, 'match_array')
24
32
  else
25
- @source_rewriter.replace(selector_range, 'match')
33
+ replace(selector_range, 'match')
26
34
  end
27
35
  parenthesize!(parenthesize_arg)
28
36
  end
@@ -34,15 +42,15 @@ module Transpec
34
42
  case left_parenthesis_range.source
35
43
  when ' '
36
44
  if always || arg_node.type == :hash
37
- @source_rewriter.replace(left_parenthesis_range, '(')
38
- @source_rewriter.insert_after(expression_range, ')')
45
+ replace(left_parenthesis_range, '(')
46
+ insert_after(expression_range, ')')
39
47
  end
40
48
  when "\n", "\r"
41
- @source_rewriter.insert_before(left_parenthesis_range, '(')
49
+ insert_before(left_parenthesis_range, '(')
42
50
  linefeed = left_parenthesis_range.source
43
51
  matcher_line_indentation = indentation_of_line(@node)
44
52
  right_parenthesis = "#{linefeed}#{matcher_line_indentation})"
45
- @source_rewriter.insert_after(expression_range, right_parenthesis)
53
+ insert_after(expression_range, right_parenthesis)
46
54
  end
47
55
  end
48
56
 
@@ -1,26 +1,20 @@
1
1
  # coding: utf-8
2
2
 
3
+ require 'transpec/syntax'
4
+ require 'transpec/syntax/any_instanceable'
5
+ require 'transpec/util'
3
6
  require 'English'
4
7
 
5
8
  module Transpec
6
9
  class Syntax
7
10
  class MethodStub < Syntax
8
- include SendNodeSyntax, Util
9
-
10
- def self.target_node?(node)
11
- return false unless node.type == :send
12
- receiver_node, method_name, *_ = *node
13
- return false unless receiver_node
14
- [:stub, :unstub, :stub!, :unstub!].include?(method_name)
15
- end
11
+ include AnyInstanceable, Util
16
12
 
17
13
  def allowize!
18
14
  # There's no way of unstubbing in #allow syntax.
19
15
  return unless [:stub, :stub!].include?(method_name)
20
16
 
21
- if @replaced_deprecated_method
22
- fail 'Already replaced deprecated method, cannot allowize.'
23
- end
17
+ fail 'Already replaced deprecated method, cannot allowize.' if @replaced_deprecated_method
24
18
 
25
19
  unless in_example_group_context?
26
20
  fail NotInExampleGroupContextError.new(expression_range, "##{method_name}", '#allow')
@@ -28,10 +22,10 @@ module Transpec
28
22
 
29
23
  if arg_node.type == :hash
30
24
  expressions = build_allow_expressions_from_hash_node(arg_node)
31
- @source_rewriter.replace(expression_range, expressions)
25
+ replace(expression_range, expressions)
32
26
  else
33
27
  expression = build_allow_expression(arg_node)
34
- @source_rewriter.replace(expression_range, expression)
28
+ replace(expression_range, expression)
35
29
  end
36
30
 
37
31
  @allowized = true
@@ -45,17 +39,23 @@ module Transpec
45
39
 
46
40
  return unless replacement_method_name
47
41
 
48
- if @allowized
49
- fail 'Already allowized, cannot replace deprecated method.'
50
- end
42
+ fail 'Already allowized, cannot replace deprecated method.' if @allowized
51
43
 
52
- @source_rewriter.replace(selector_range, replacement_method_name)
44
+ replace(selector_range, replacement_method_name)
53
45
 
54
46
  @replaced_deprecated_method = true
55
47
  end
56
48
 
57
49
  private
58
50
 
51
+ def self.target_receiver_node?(node)
52
+ !node.nil?
53
+ end
54
+
55
+ def self.target_method_names
56
+ [:stub, :unstub, :stub!, :unstub!]
57
+ end
58
+
59
59
  def build_allow_expressions_from_hash_node(hash_node)
60
60
  expressions = []
61
61
 
@@ -70,15 +70,7 @@ module Transpec
70
70
  end
71
71
 
72
72
  def build_allow_expression(message_node, return_value_node = nil, keep_form_around_arg = true)
73
- expression = ''
74
-
75
- expression << if any_instance?
76
- class_source = class_node_of_any_instance.loc.expression.source
77
- "allow_any_instance_of(#{class_source})"
78
- else
79
- "allow(#{subject_range.source})"
80
- end
81
-
73
+ expression = allow_source
82
74
  expression << range_in_between_subject_and_selector.source
83
75
  expression << 'to receive'
84
76
  expression << (keep_form_around_arg ? range_in_between_selector_and_arg.source : '(')
@@ -93,24 +85,18 @@ module Transpec
93
85
  expression
94
86
  end
95
87
 
96
- def class_node_of_any_instance
97
- return nil unless subject_node.type == :send
98
- return nil unless subject_node.children.count == 2
99
- receiver_node, method_name = *subject_node
100
- return nil unless method_name == :any_instance
101
- return nil unless receiver_node.type == :const
102
- receiver_node
103
- end
104
-
105
- def any_instance?
106
- !class_node_of_any_instance.nil?
88
+ def allow_source
89
+ if any_instance?
90
+ class_source = class_node_of_any_instance.loc.expression.source
91
+ "allow_any_instance_of(#{class_source})"
92
+ else
93
+ "allow(#{subject_range.source})"
94
+ end
107
95
  end
108
96
 
109
97
  def message_source(node)
110
98
  message_source = node.loc.expression.source
111
- if node.type == :sym && !message_source.start_with?(':')
112
- message_source.prepend(':')
113
- end
99
+ message_source.prepend(':') if node.type == :sym && !message_source.start_with?(':')
114
100
  message_source
115
101
  end
116
102
 
@@ -1,5 +1,7 @@
1
1
  # coding: utf-8
2
2
 
3
+ require 'transpec/syntax'
4
+
3
5
  module Transpec
4
6
  class Syntax
5
7
  module SendNodeSyntax
@@ -17,10 +19,6 @@ module Transpec
17
19
  @node.children[2]
18
20
  end
19
21
 
20
- def expression_range
21
- @node.loc.expression
22
- end
23
-
24
22
  def selector_range
25
23
  @node.loc.selector
26
24
  end
@@ -1,16 +1,14 @@
1
1
  # coding: utf-8
2
2
 
3
+ require 'transpec/syntax'
4
+ require 'transpec/syntax/expectizable'
5
+ require 'transpec/syntax/matcher'
6
+ require 'transpec/util'
7
+
3
8
  module Transpec
4
9
  class Syntax
5
10
  class Should < Syntax
6
- include SendNodeSyntax, Util
7
-
8
- def self.target_node?(node)
9
- return false unless node.type == :send
10
- receiver_node, method_name, *_ = *node
11
- return false unless receiver_node
12
- [:should, :should_not].include?(method_name)
13
- end
11
+ include Expectizable, Util
14
12
 
15
13
  def positive?
16
14
  method_name == :should
@@ -22,17 +20,12 @@ module Transpec
22
20
  end
23
21
 
24
22
  if proc_literal?(subject_node)
25
- send_node = subject_node.children.first
26
- range_of_subject_method_taking_block = send_node.loc.expression
27
- @source_rewriter.replace(range_of_subject_method_taking_block, 'expect')
28
- elsif subject_range.source[0] == '('
29
- @source_rewriter.insert_before(subject_range, 'expect')
23
+ replace_proc_selector_with_expect!
30
24
  else
31
- @source_rewriter.insert_before(subject_range, 'expect(')
32
- @source_rewriter.insert_after(subject_range, ')')
25
+ wrap_subject_in_expect!
33
26
  end
34
27
 
35
- @source_rewriter.replace(selector_range, positive? ? 'to' : negative_form)
28
+ replace(selector_range, positive? ? 'to' : negative_form)
36
29
 
37
30
  matcher.correct_operator!(parenthesize_matcher_arg)
38
31
  end
@@ -44,6 +37,22 @@ module Transpec
44
37
  def matcher_node
45
38
  arg_node || parent_node
46
39
  end
40
+
41
+ private
42
+
43
+ def self.target_receiver_node?(node)
44
+ !node.nil?
45
+ end
46
+
47
+ def self.target_method_names
48
+ [:should, :should_not]
49
+ end
50
+
51
+ def replace_proc_selector_with_expect!
52
+ send_node = subject_node.children.first
53
+ range_of_subject_method_taking_block = send_node.loc.expression
54
+ replace(range_of_subject_method_taking_block, 'expect')
55
+ end
47
56
  end
48
57
  end
49
58
  end
@@ -1,16 +1,13 @@
1
1
  # coding: utf-8
2
2
 
3
+ require 'transpec/syntax'
4
+ require 'transpec/syntax/expectizable'
5
+ require 'transpec/syntax/any_instanceable'
6
+
3
7
  module Transpec
4
8
  class Syntax
5
9
  class ShouldReceive < Syntax
6
- include SendNodeSyntax
7
-
8
- def self.target_node?(node)
9
- return false unless node.type == :send
10
- receiver_node, method_name, *_ = *node
11
- return false unless receiver_node
12
- [:should_receive, :should_not_receive].include?(method_name)
13
- end
10
+ include Expectizable, AnyInstanceable
14
11
 
15
12
  def positive?
16
13
  method_name == :should_receive
@@ -21,46 +18,50 @@ module Transpec
21
18
  fail NotInExampleGroupContextError.new(expression_range, "##{method_name}", '#expect')
22
19
  end
23
20
 
24
- if any_instance?(subject_node)
25
- @source_rewriter.insert_before(subject_range, 'expect_any_instance_of(')
26
- map = subject_node.loc
27
- dot_any_instance_range = map.dot.join(map.selector)
28
- @source_rewriter.replace(dot_any_instance_range, ')')
21
+ if any_instance?
22
+ wrap_class_in_expect_any_instance_of!
29
23
  else
30
- @source_rewriter.insert_before(subject_range, 'expect(')
31
- @source_rewriter.insert_after(subject_range, ')')
24
+ wrap_subject_in_expect!
32
25
  end
33
26
 
34
- to_receive = "#{positive? ? 'to' : negative_form} receive"
35
- @source_rewriter.replace(selector_range, to_receive)
27
+ replace(selector_range, "#{positive? ? 'to' : negative_form} receive")
36
28
 
37
29
  correct_block_style!
38
30
  end
39
31
 
40
32
  def correct_block_style!
41
- broken_block_nodes = [
42
- block_node_taken_by_with_method_with_no_normal_args,
43
- block_node_followed_by_message_expectation_method
44
- ].compact.uniq
45
-
46
33
  return if broken_block_nodes.empty?
47
34
 
48
35
  broken_block_nodes.each do |block_node|
49
36
  map = block_node.loc
50
37
  next if map.begin.source == '{'
51
- @source_rewriter.replace(map.begin, '{')
52
- @source_rewriter.replace(map.end, '}')
38
+ replace(map.begin, '{')
39
+ replace(map.end, '}')
53
40
  end
54
41
  end
55
42
 
56
43
  private
57
44
 
58
- def any_instance?(node)
59
- return false unless node.type == :send
60
- return false unless node.children.count == 2
61
- receiver_node, method_name = *node
62
- return false unless method_name == :any_instance
63
- receiver_node.type == :const
45
+ def self.target_receiver_node?(node)
46
+ !node.nil?
47
+ end
48
+
49
+ def self.target_method_names
50
+ [:should_receive, :should_not_receive]
51
+ end
52
+
53
+ def wrap_class_in_expect_any_instance_of!
54
+ insert_before(subject_range, 'expect_any_instance_of(')
55
+ map = subject_node.loc
56
+ dot_any_instance_range = map.dot.join(map.selector)
57
+ replace(dot_any_instance_range, ')')
58
+ end
59
+
60
+ def broken_block_nodes
61
+ @broken_block_nodes ||= [
62
+ block_node_taken_by_with_method_with_no_normal_args,
63
+ block_node_followed_by_message_expectation_method
64
+ ].compact.uniq
64
65
  end
65
66
 
66
67
  # subject.should_receive(:method_name).once.with do |block_arg|
@@ -105,11 +106,7 @@ module Transpec
105
106
  @ancestor_nodes.reverse.reduce(@node) do |child_node, parent_node|
106
107
  return nil unless [:send, :block].include?(parent_node.type)
107
108
  return nil unless parent_node.children.first == child_node
108
-
109
- if child_node.type == :block && parent_node.type == :send
110
- return child_node
111
- end
112
-
109
+ return child_node if child_node.type == :block && parent_node.type == :send
113
110
  parent_node
114
111
  end
115
112