rspec 0.6.4 → 0.7.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 (114) hide show
  1. data/CHANGES +90 -1
  2. data/EXAMPLES.rd +28 -6
  3. data/MIT-LICENSE +20 -0
  4. data/README +18 -12
  5. data/Rakefile +60 -54
  6. data/examples/custom_formatter.rb +4 -4
  7. data/examples/helper_method_example.rb +11 -0
  8. data/examples/mocking_example.rb +19 -2
  9. data/examples/partial_mock_example.rb +28 -0
  10. data/examples/stack_spec.rb +8 -8
  11. data/examples/stubbing_example.rb +50 -9
  12. data/examples/test_case_spec.rb +6 -6
  13. data/lib/spec.rb +1 -2
  14. data/lib/spec/callback.rb +0 -0
  15. data/lib/spec/expectations.rb +3 -6
  16. data/lib/spec/expectations/diff.rb +23 -47
  17. data/lib/spec/expectations/differs/default.rb +62 -0
  18. data/lib/spec/expectations/{exceptions.rb → errors.rb} +0 -0
  19. data/lib/spec/expectations/extensions.rb +4 -0
  20. data/lib/spec/expectations/extensions/inspect_for_expectation_not_met_error.rb +14 -0
  21. data/lib/spec/expectations/extensions/numeric.rb +5 -0
  22. data/lib/spec/expectations/{expectations.rb → extensions/object.rb} +3 -6
  23. data/lib/spec/expectations/extensions/symbol.rb +5 -0
  24. data/lib/spec/expectations/should.rb +4 -0
  25. data/lib/spec/expectations/should/base.rb +42 -0
  26. data/lib/spec/expectations/should/have.rb +79 -0
  27. data/lib/spec/expectations/should/not.rb +72 -0
  28. data/lib/spec/expectations/should/should.rb +83 -0
  29. data/lib/spec/expectations/sugar.rb +6 -25
  30. data/lib/spec/mocks.rb +5 -1
  31. data/lib/spec/mocks/argument_expectation.rb +15 -1
  32. data/lib/spec/mocks/error_generator.rb +72 -0
  33. data/lib/spec/mocks/{exceptions.rb → errors.rb} +0 -0
  34. data/lib/spec/mocks/extensions/object.rb +3 -0
  35. data/lib/spec/mocks/message_expectation.rb +80 -73
  36. data/lib/spec/mocks/mock.rb +4 -69
  37. data/lib/spec/mocks/mock_handler.rb +158 -0
  38. data/lib/spec/mocks/mock_methods.rb +44 -0
  39. data/lib/spec/mocks/order_group.rb +10 -2
  40. data/lib/spec/rake/spectask.rb +20 -18
  41. data/lib/spec/rake/{rcov_verify.rb → verify_rcov.rb} +2 -2
  42. data/lib/spec/runner.rb +3 -1
  43. data/lib/spec/runner/backtrace_tweaker.rb +2 -1
  44. data/lib/spec/runner/context.rb +10 -16
  45. data/lib/spec/runner/context_eval.rb +40 -40
  46. data/lib/spec/runner/execution_context.rb +1 -12
  47. data/lib/spec/runner/{kernel_ext.rb → extensions/kernel.rb} +2 -2
  48. data/lib/spec/runner/{instance_exec.rb → extensions/object.rb} +0 -0
  49. data/lib/spec/runner/formatter/base_text_formatter.rb +25 -18
  50. data/lib/spec/runner/formatter/html_formatter.rb +81 -101
  51. data/lib/spec/runner/formatter/progress_bar_formatter.rb +9 -9
  52. data/lib/spec/runner/formatter/rdoc_formatter.rb +6 -6
  53. data/lib/spec/runner/formatter/specdoc_formatter.rb +7 -6
  54. data/lib/spec/runner/option_parser.rb +41 -5
  55. data/lib/spec/runner/reporter.rb +3 -15
  56. data/lib/spec/runner/spec_should_raise_handler.rb +74 -0
  57. data/lib/spec/runner/specification.rb +33 -14
  58. data/lib/spec/version.rb +6 -3
  59. data/vendor/watir/README.txt +1 -1
  60. metadata +34 -68
  61. data/bin/test2spec +0 -112
  62. data/examples/helper_method_spec.rb +0 -12
  63. data/lib/spec/expectations/have_helper.rb +0 -41
  64. data/lib/spec/expectations/helper.rb +0 -4
  65. data/lib/spec/expectations/should_base.rb +0 -52
  66. data/lib/spec/expectations/should_helper.rb +0 -93
  67. data/lib/spec/expectations/should_negator.rb +0 -71
  68. data/lib/spec/test_to_spec/ruby2ruby.rb +0 -492
  69. data/lib/spec/test_to_spec/sexp_transformer.rb +0 -196
  70. data/lib/spec/test_to_spec/test_case_ext.rb +0 -22
  71. data/lib/spec/test_to_spec/translation_test_runner.rb +0 -147
  72. data/test/spec/expectations/arbitrary_operator_test.rb +0 -55
  73. data/test/spec/expectations/arbitrary_predicate_test.rb +0 -163
  74. data/test/spec/expectations/containment_test.rb +0 -129
  75. data/test/spec/expectations/diff_test.rb +0 -62
  76. data/test/spec/expectations/identity_test.rb +0 -75
  77. data/test/spec/expectations/object_equality_test.rb +0 -65
  78. data/test/spec/expectations/raising_test.rb +0 -106
  79. data/test/spec/expectations/regex_matching_test.rb +0 -36
  80. data/test/spec/expectations/should_have_test.rb +0 -169
  81. data/test/spec/expectations/should_satisfy_test.rb +0 -37
  82. data/test/spec/expectations/sugar_test.rb +0 -93
  83. data/test/spec/expectations/supported_symbols_test.rb +0 -33
  84. data/test/spec/expectations/throwing_test.rb +0 -55
  85. data/test/spec/expectations/true_false_special_case_test.rb +0 -85
  86. data/test/spec/expectations/typing_test.rb +0 -108
  87. data/test/spec/mocks/mock_arg_constraints_test.rb +0 -113
  88. data/test/spec/mocks/mock_counts_test.rb +0 -431
  89. data/test/spec/mocks/mock_ordering_test.rb +0 -109
  90. data/test/spec/mocks/mock_test.rb +0 -220
  91. data/test/spec/mocks/null_object_test.rb +0 -37
  92. data/test/spec/runner/backtrace_tweaker_test.rb +0 -90
  93. data/test/spec/runner/context_matching_test.rb +0 -35
  94. data/test/spec/runner/context_runner_test.rb +0 -62
  95. data/test/spec/runner/context_test.rb +0 -191
  96. data/test/spec/runner/execution_context_test.rb +0 -45
  97. data/test/spec/runner/formatter/failure_dump_test.rb +0 -94
  98. data/test/spec/runner/formatter/html_formatter_test.rb +0 -48
  99. data/test/spec/runner/formatter/progress_bar_formatter_test.rb +0 -56
  100. data/test/spec/runner/formatter/rdoc_formatter_test.rb +0 -51
  101. data/test/spec/runner/formatter/specdoc_formatter_test.rb +0 -57
  102. data/test/spec/runner/kernel_ext_test.rb +0 -13
  103. data/test/spec/runner/option_parser_test.rb +0 -141
  104. data/test/spec/runner/reporter_test.rb +0 -128
  105. data/test/spec/runner/spec_matcher_test.rb +0 -47
  106. data/test/spec/runner/specification_test.rb +0 -121
  107. data/test/spec/test_to_spec/ruby_to_ruby_test.rb +0 -79
  108. data/test/spec/test_to_spec/sexp_transformer_assertion_test.rb +0 -207
  109. data/test/spec/test_to_spec/sexp_transformer_test.rb +0 -303
  110. data/test/spec/test_to_spec/test_case_ext_test.rb +0 -25
  111. data/test/spec/test_to_spec/testfiles/test_unit_api_spec.rb +0 -75
  112. data/test/spec/test_to_spec/testfiles/test_unit_api_test.rb +0 -70
  113. data/test/test_classes.rb +0 -102
  114. data/test/test_helper.rb +0 -32
@@ -1,112 +0,0 @@
1
- #!/usr/bin/env ruby
2
-
3
- require 'test/unit'
4
- require 'test/unit/ui/console/testrunner'
5
- require 'test/unit/ui/testrunnerutilities'
6
- require 'test/unit/ui/testrunnermediator'
7
- require 'test/unit/autorunner'
8
- require 'optparse'
9
-
10
- $LOAD_PATH.unshift File.dirname(__FILE__) + '/../lib'
11
-
12
- require 'rubygems'
13
- require 'spec/test_to_spec/translation_test_runner'
14
- require 'spec/version'
15
-
16
- $test2spec_options = {
17
- :collision => :ask,
18
- :verbose => false
19
- }
20
-
21
- opts = OptionParser.new do |opts|
22
- opts.banner = "Usage: test2spec [options] (FILE|DIRECTORY|GLOB)+"
23
- opts.separator ""
24
-
25
- opts.on("-s", "--specdir DIRECTORY", "Directory where specs will be written") do |dir|
26
- $test2spec_options[:specdir] = dir
27
- end
28
-
29
- opts.on("-t", "--template FILE",
30
- "ERB template that will be used to decorate each translated file.",
31
- "The template has access to the following variables:",
32
- " translation : the translated source code",
33
- " depth : the directory depth of the file to be written",
34
- " relative_path : the relative name of the file to be written"
35
- ) do |file|
36
- $test2spec_options[:template] = file
37
- end
38
-
39
- opts.on("-c", "--chmod MODIFIERS", Integer, "Change file modifiers on written files (POSIX only)") do |mods|
40
- $test2spec_options[:chmod] = mods
41
- end
42
-
43
- opts.on("--svn", "Add written files to subversion") do
44
- $test2spec_options[:svn] = true
45
- end
46
-
47
- opts.on("-f", "--force", "Forcefully overwrite existing specs") do
48
- $test2spec_options[:collision] = :force
49
- end
50
-
51
- opts.on("-q", "--quiet", "Don't print anything to stdout") do
52
- $test2spec_options[:quiet] = true
53
- end
54
-
55
- opts.on("--verbose", "Be extra verbose (printing backtraces when classes can't be translated)") do
56
- $test2spec_options[:verbose] = true
57
- end
58
-
59
- opts.on("-v", "--version", "Show version") do
60
- puts "test2spec #{Spec::VERSION::DESCRIPTION}"
61
- exit
62
- end
63
-
64
- opts.on("-d", "--dry-run", "Don't write anything - just verify that translation works") do
65
- $test2spec_options[:dry_run] = true
66
- end
67
-
68
- opts.on_tail("-h", "--help", "You're looking at it") do
69
- puts opts
70
- exit
71
- end
72
- end
73
-
74
- opts.parse! ARGV
75
-
76
- if($test2spec_options[:specdir].nil?)
77
- STDERR.puts "ERROR: --specdir must be specified"
78
- puts opts
79
- exit 1
80
- end
81
-
82
- if(ARGV.empty?)
83
- STDERR.puts "ERROR: At least one directory, file or glob must be specified"
84
- puts opts
85
- exit 1
86
- end
87
-
88
- module Test
89
- module Unit
90
- class AutoRunner
91
- def initialize(standalone)
92
- @standalone = standalone
93
- @runner = proc { |r| Spec::TestToSpec::TranslationTestRunner }
94
- @collector = COLLECTORS[(standalone ? :dir : :objectspace)]
95
- @filters = []
96
- @to_run = []
97
- yield(self) if(block_given?)
98
- end
99
- end
100
- end
101
- end
102
-
103
- # If ARGV is a glob, it will actually each over each one of the matching files.
104
- ARGV.each do |arg|
105
- if File.directory?(arg)
106
- Dir["#{arg}/**/*.rb"].each do |file|
107
- require "#{file}"
108
- end
109
- else
110
- require arg
111
- end
112
- end
@@ -1,12 +0,0 @@
1
- require File.dirname(__FILE__) + '/../lib/spec'
2
-
3
- context "Rspec" do
4
- specify "should allow you to define helper methods" do
5
- a_method
6
- @a_method_called.should_be true
7
- end
8
-
9
- def a_method
10
- @a_method_called = true
11
- end
12
- end
@@ -1,41 +0,0 @@
1
- module Spec
2
- module Expectations
3
- class HaveHelper < ShouldBase
4
-
5
- def initialize(target, relativity=:exactly, expected=nil)
6
- @target = target
7
- @expected = expected == :no ? 0 : expected
8
- @at_least = (relativity == :at_least)
9
- @at_most = (relativity == :at_most)
10
- end
11
-
12
- def method_missing(sym, *args)
13
- fail_with_message(build_message(sym, args)) unless as_specified?(sym, args)
14
- end
15
-
16
- def collection(sym, args)
17
- @target.send(sym, *args)
18
- end
19
-
20
- def actual_size(collection)
21
- return collection.length if collection.respond_to? :length
22
- return collection.size if collection.respond_to? :size
23
- end
24
-
25
- def build_message(sym, args)
26
- message = "#{@target.inspect_for_expectation_not_met_error} should have"
27
- message += " at least" if @at_least
28
- message += " at most" if @at_most
29
- message += " #{@expected} #{sym} (has #{actual_size(collection(sym, args))})"
30
- end
31
-
32
- def as_specified?(sym, args)
33
- return actual_size(collection(sym, args)) >= @expected if @at_least
34
- return actual_size(collection(sym, args)) <= @expected if @at_most
35
- return actual_size(collection(sym, args)) == @expected
36
- end
37
-
38
- end
39
- end
40
-
41
- end
@@ -1,4 +0,0 @@
1
- require 'spec/expectations/helper/should_base'
2
- require 'spec/expectations/helper/have_helper'
3
- require 'spec/expectations/helper/should_helper'
4
- require 'spec/expectations/helper/should_negator'
@@ -1,52 +0,0 @@
1
- class Symbol
2
- def supported_by_rspec?
3
- return ["<","<=",">=",">","==","=~"].include?(to_s)
4
- end
5
- end
6
- class Object
7
- def inspect_for_expectation_not_met_error
8
- return "#{inspect}" if inspect.include? "<"
9
- return "<#{inspect}>" unless inspect.include? "<"
10
- end
11
- end
12
- class TrueClass; def inspect_for_expectation_not_met_error; "true" end end
13
- class FalseClass; def inspect_for_expectation_not_met_error; "false" end end
14
- class NilClass; def inspect_for_expectation_not_met_error; "nil" end end
15
- class Class; def inspect_for_expectation_not_met_error; "<#{name}>" end end
16
- class Proc; def inspect_for_expectation_not_met_error; "<Proc>" end end
17
- class Array; def inspect_for_expectation_not_met_error; inspect end end
18
- class String; def inspect_for_expectation_not_met_error; inspect end end
19
- class Numeric; def inspect_for_expectation_not_met_error; inspect end end
20
-
21
- module Spec
22
- module Expectations
23
- class ShouldBase
24
-
25
- instance_methods.each { |m| undef_method m unless m =~ /^(__|\w)/ }
26
-
27
- def default_message(expectation, expected=:no_expectation_specified)
28
- message = "#{@target.inspect_for_expectation_not_met_error} #{expectation}"
29
- if (expected != :no_expectation_specified)
30
- message << " " << expected.inspect_for_expectation_not_met_error
31
- end
32
- message
33
- end
34
-
35
- def fail_with_message(message)
36
- Kernel::raise(Spec::Expectations::ExpectationNotMetError.new(message))
37
- end
38
-
39
- def respond_to? sym
40
- return true if super
41
- return true if @target.respond_to? "#{sym.to_s}?"
42
- end
43
-
44
- def find_supported_sym(original_sym)
45
- ["#{original_sym}?", "#{original_sym}s?"].each do |alternate_sym|
46
- return alternate_sym.to_s if @target.respond_to?(alternate_sym.to_s)
47
- end
48
- return original_sym.supported_by_rspec? ? original_sym : "#{original_sym}?"
49
- end
50
- end
51
- end
52
- end
@@ -1,93 +0,0 @@
1
- module Spec
2
- module Expectations
3
- class ShouldHelper < ShouldBase
4
-
5
- def initialize(target)
6
- @target = target
7
- @be_seen = false
8
- end
9
-
10
- def not
11
- ShouldNegator.new(@target)
12
- end
13
-
14
- def have(expected_number=nil)
15
- HaveHelper.new(@target, :exactly, expected_number)
16
- end
17
-
18
- def have_exactly(expected_number=nil)
19
- HaveHelper.new(@target, :exactly, expected_number)
20
- end
21
-
22
- def have_at_least(expected_number=nil)
23
- HaveHelper.new(@target, :at_least, expected_number)
24
- end
25
-
26
- def have_at_most(expected_number=nil)
27
- HaveHelper.new(@target, :at_most, expected_number)
28
- end
29
-
30
- def satisfy(&block)
31
- return if block.call(@target)
32
- fail_with_message "Supplied expectation was not satisfied"
33
- end
34
-
35
- def equal(expected)
36
- fail_with_message(default_message("should equal", expected)) unless (@target == expected)
37
- end
38
-
39
- def be(expected = :___no_arg)
40
- @be_seen = true
41
- return self if (expected == :___no_arg)
42
- return if (expected == false and @target.nil?)
43
- return if (expected == true and (!@target.nil?) and (@target != false))
44
- fail_with_message(default_message("should be", expected)) unless (@target.equal?(expected))
45
- end
46
-
47
- def an_instance_of expected_class
48
- fail_with_message(default_message("should be an instance of", expected_class)) unless @target.instance_of? expected_class
49
- end
50
-
51
- def a_kind_of expected_class
52
- fail_with_message(default_message("should be a kind of", expected_class)) unless @target.kind_of? expected_class
53
- end
54
-
55
- def respond_to message
56
- fail_with_message(default_message("should respond to", message)) unless @target.respond_to? message
57
- end
58
-
59
- def method_missing(original_sym, *args)
60
- actual_sym = find_supported_sym(original_sym)
61
- return if @target.send(actual_sym, *args)
62
- fail_with_message(default_message("should#{@be_seen ? ' be' : ''} #{original_sym}" + (args.empty? ? '' : (' ' + args.join(', ')))))
63
- end
64
-
65
- def match(expected)
66
- fail_with_message(default_message("should match", expected)) unless (@target =~ expected)
67
- end
68
-
69
- def raise(exception=Exception, message=nil)
70
- begin
71
- @target.call
72
- rescue exception => e
73
- e.message.should_equal message unless message.nil?
74
- return
75
- rescue => e
76
- fail_with_message("#{default_message("should raise", exception)} but raised #{e.inspect}")
77
- end
78
- fail_with_message("#{default_message("should raise", exception)} but raised nothing")
79
- end
80
-
81
- def throw(symbol)
82
- begin
83
- catch symbol do
84
- @target.call
85
- fail_with_message(default_message("should throw", symbol.inspect))
86
- end
87
- rescue NameError
88
- fail_with_message(default_message("should throw", symbol.inspect))
89
- end
90
- end
91
- end
92
- end
93
- end
@@ -1,71 +0,0 @@
1
- module Spec
2
- module Expectations
3
- class ShouldNegator < ShouldBase
4
-
5
- def initialize(target)
6
- @target = target
7
- @be_seen = false
8
- end
9
-
10
- def satisfy
11
- fail_with_message "Supplied expectation was satisfied, but should not have been" if (yield @target)
12
- end
13
-
14
- def equal(expected)
15
- fail_with_message(default_message("should not equal", expected)) if (@target == expected)
16
- end
17
-
18
- def be(expected = :no_arg)
19
- @be_seen = true
20
- return self if (expected == :no_arg)
21
- fail_with_message(default_message("should not be", expected)) if (@target.equal?(expected))
22
- end
23
-
24
- def an_instance_of expected_class
25
- fail_with_message(default_message("should not be an instance of", expected_class)) if @target.instance_of? expected_class
26
- end
27
-
28
- def a_kind_of expected_class
29
- fail_with_message(default_message("should not be a kind of", expected_class)) if @target.kind_of? expected_class
30
- end
31
-
32
- def respond_to message
33
- fail_with_message(default_message("should not respond to", message)) if @target.respond_to? message
34
- end
35
-
36
- def match(expected)
37
- fail_with_message(default_message("should not match", expected)) if (@target =~ expected)
38
- end
39
-
40
- def raise(exception=Exception, message=nil)
41
- begin
42
- @target.call
43
- rescue exception => e
44
- return unless message.nil? || e.message == message
45
- fail_with_message("#{default_message("should not raise", exception)}") if e.instance_of? exception
46
- fail_with_message("#{default_message("should not raise", exception)} but raised #{e.inspect}") unless e.instance_of? exception
47
- rescue
48
- true
49
- end
50
- end
51
-
52
- def throw(symbol=:___this_is_a_symbol_that_will_likely_never_occur___)
53
- begin
54
- catch symbol do
55
- @target.call
56
- return true
57
- end
58
- fail_with_message(default_message("should not throw", symbol.inspect))
59
- rescue NameError
60
- true
61
- end
62
- end
63
-
64
- def method_missing(original_sym, *args)
65
- actual_sym = find_supported_sym(original_sym)
66
- return unless @target.__send__(actual_sym, *args)
67
- fail_with_message(default_message("should not#{@be_seen ? ' be' : ''} #{original_sym}" + (args.empty? ? '' : (' ' + args.join(', ')))))
68
- end
69
- end
70
- end
71
- end
@@ -1,492 +0,0 @@
1
- # Taken from http://dark.fhtr.org/ruby2ruby.rb
2
-
3
- require 'pp'
4
- require 'rubygems'
5
- begin
6
- require 'parse_tree'
7
- require 'sexp_processor'
8
- rescue LoadError
9
- raise "You must gem install ParseTree (and RubyInline)"
10
- end
11
-
12
- class RubySource < String
13
-
14
- def inspect
15
- "\n"+to_s
16
- end
17
-
18
- end
19
-
20
-
21
- class Object
22
-
23
- def parse_tree(method_name=nil)
24
- if method_name
25
- m = method(method_name)
26
- klass = m.defined_in
27
- method_name = m.name
28
- return ParseTree.new.parse_tree_for_method(klass, method_name)
29
- elsif is_a?(Class)
30
- klass = self
31
- else
32
- klass = self.class
33
- end
34
- ParseTree.new.parse_tree(klass).first
35
- end
36
-
37
- def source(method_name=nil)
38
- RubySource.new RubyToRuby.new.process(parse_tree(method_name))
39
- end
40
-
41
- end
42
-
43
-
44
- class Method
45
-
46
- def defined_in
47
- full_name = to_s.split(" ").last.chop
48
- klass_name = full_name.split(/[\#\.]/).first
49
- if klass_name.include?("(")
50
- klass_name = klass_name.split("(").last.chop
51
- end
52
- klass = klass_name.split("::").inject(Object){|o,n| o.const_get(n)}
53
- klass
54
- end
55
-
56
- def name
57
- full_name = to_s.split(" ").last.chop
58
- full_name.split(/[\#\.]/).last
59
- end
60
-
61
- end
62
-
63
- class RubyToRuby < SexpProcessor
64
-
65
- def self.translate(klass, method=nil)
66
- RubySource.new(
67
- unless method.nil? then
68
- self.new.process(ParseTree.new.parse_tree_for_method(klass, method))
69
- else
70
- self.new.process(ParseTree.new.parse_tree(klass).first) # huh? why is the :class node wrapped?
71
- end
72
- )
73
- end
74
-
75
- def initialize
76
- super
77
- @block_params = false
78
- @indent = " "
79
- self.auto_shift_type = true
80
- self.strict = true
81
- self.expected = String
82
- end
83
-
84
- def indent(s)
85
- s.to_s.map{|line| @indent + line}.join
86
- end
87
-
88
- def process_and(exp)
89
- "(#{process exp.shift} and #{process exp.shift})"
90
- end
91
-
92
- def process_args(exp)
93
- args = []
94
-
95
- until exp.empty? do
96
- arg = exp.shift
97
- if arg.is_a? Array
98
- args[-(arg.size-1)..-1] = arg[1..-1].map{|a| process a}
99
- else
100
- args << arg
101
- end
102
- end
103
-
104
- args.empty? ? "" : "(#{args.join ', '})"
105
- end
106
-
107
- def process_array(exp)
108
- code = []
109
- until exp.empty? do
110
- code << process(exp.shift)
111
- end
112
- return "[" + code.join(", ") + "]"
113
- end
114
-
115
- def process_attrasgn(exp)
116
- process_call(exp)
117
- end
118
-
119
- def process_begin(exp)
120
- s = "begin\n"
121
- s << (process(exp.shift).to_s + "\n") until exp.empty?
122
- s + "\nend"
123
- end
124
-
125
- def process_block(exp)
126
- code = []
127
- catch_block_arg = false
128
- until exp.empty? do
129
- if catch_block_arg
130
- if exp.first and exp.first.first == :block_arg
131
- code[-1] = code[-1][0..-2] + ", #{process(exp.shift)})"
132
- end
133
- catch_block_arg = false
134
- else
135
- if exp.first.first == :args
136
- catch_block_arg = true
137
- end
138
- if [:ensure, :rescue].include? exp.first.first
139
- code << process(exp.shift)
140
- else
141
- code << indent(process(exp.shift))
142
- end
143
- end
144
- end
145
-
146
- body = code.join("\n")
147
- body += "\n"
148
-
149
- return body
150
- end
151
-
152
- def process_block_arg(exp)
153
- "&#{exp.shift}"
154
- end
155
-
156
- def process_block_pass(exp)
157
- bname = process(exp.shift)
158
- fcall = process(exp.shift)
159
- if fcall[-1,1] == ')'
160
- "#{fcall[0..-2]}, &(#{bname}))"
161
- else
162
- "#{fcall}(&(#{bname}))"
163
- end
164
- end
165
-
166
- def process_call(exp)
167
- receiver = process exp.shift
168
- name = exp.shift
169
- args_exp = exp.shift
170
- if args_exp && args_exp.first == :array
171
- args = "#{process(args_exp)[1..-2]}"
172
- else
173
- args = process args_exp
174
- end
175
-
176
- case name
177
- when :<=>, :==, :<, :>, :<=, :>=, :-, :+, :*, :/, :% then #
178
- "(#{receiver} #{name} #{args})"
179
- when :[] then
180
- "#{receiver}[#{args}]"
181
- else
182
- "#{receiver}.#{name}#{args ? "(#{args})" : args}"
183
- end
184
- end
185
-
186
- def process_case(exp)
187
- s = "case #{process exp.shift}\n"
188
- until exp.empty?
189
- pt = exp.shift
190
- if pt and pt.first == :when
191
- s << "#{process(pt)}\n"
192
- else
193
- s << "else\n#{indent(process(pt))}\n"
194
- end
195
- end
196
- s + "\nend"
197
- end
198
-
199
- def process_class(exp)
200
- s = "class #{exp.shift} < #{exp.shift}\n"
201
- body = ""
202
- body << "#{process exp.shift}\n\n" until exp.empty?
203
- s + indent(body) + "end"
204
- end
205
-
206
- def process_colon2(exp)
207
- "#{process(exp.shift)}::#{exp.shift}"
208
- end
209
-
210
- def process_const(exp)
211
- exp.shift.to_s
212
- end
213
-
214
- def process_dasgn_curr(exp)
215
- s = exp.shift.to_s
216
- unless exp.empty?
217
- s += "=" + process(exp.shift)
218
- else
219
- if(@block_params)
220
- s
221
- else
222
- ""
223
- end
224
- end
225
- end
226
-
227
- def process_defn(exp)
228
- if exp[1].first == :cfunc
229
- s = "# method '#{exp.shift}' defined in a C function"
230
- exp.shift
231
- return s
232
- else
233
- name = exp.shift
234
- args = process(exp.shift)
235
- return "def #{name}#{args}end".gsub(/\n\s*\n+/, "\n")
236
- end
237
- end
238
-
239
- def process_dot2(exp)
240
- "(#{process exp.shift}..#{process exp.shift})"
241
- end
242
-
243
- def process_dot3(exp)
244
- "(#{process exp.shift}...#{process exp.shift})"
245
- end
246
-
247
- def process_dstr(exp)
248
- s = exp.shift.dump[0..-2]
249
- until exp.empty?
250
- pt = exp.shift
251
- if pt.first == :str
252
- s << process(pt)[1..-2]
253
- else
254
- s << '#{' + process(pt) + '}'
255
- end
256
- end
257
- s + '"'
258
- end
259
-
260
- def process_dvar(exp)
261
- exp.shift.to_s
262
- end
263
-
264
- def process_ensure(exp)
265
- process(exp.shift) + "\n" +
266
- "ensure\n" +
267
- indent(process(exp.shift))
268
- end
269
-
270
- def process_false(exp)
271
- "false"
272
- end
273
-
274
- def process_fbody(exp)
275
- process(exp.shift)
276
- end
277
-
278
- def process_fcall(exp)
279
- exp_orig = exp.deep_clone
280
- # [:fcall, :puts, [:array, [:str, "This is a weird loop"]]]
281
- name = exp.shift.to_s
282
- args = exp.shift
283
- code = []
284
- unless args.nil? then
285
- assert_type args, :array
286
- args.shift # :array
287
- until args.empty? do
288
- code << process(args.shift)
289
- end
290
- end
291
- return "#{name}(#{code.join(', ')})"
292
- end
293
-
294
- def process_for(exp)
295
- s = "for #{process(exp[1])} in #{process(exp[0])}\n"
296
- 2.times{ exp.shift }
297
- s += indent("#{process(exp.shift)}\n")
298
- s += "end"
299
- end
300
-
301
- def process_gvar(exp)
302
- exp.shift.to_s
303
- end
304
-
305
- def process_hash(exp)
306
- body = []
307
- body << "#{process(exp.shift)} => #{process(exp.shift)}" until exp.empty?
308
- body_str = ""
309
- body_str = "\n"+indent(body.join(",\n"))+"\n" unless body.empty?
310
- "{" + body_str + "}"
311
- end
312
-
313
- def process_iasgn(exp)
314
- "#{exp.shift} = #{process exp.shift}"
315
- end
316
-
317
- def cond_indent_process(pt)
318
- (pt and pt.first == :block) ? process(pt) : indent(process(pt))
319
- end
320
-
321
- def process_if(exp)
322
- s = ["if (#{process exp.shift})"]
323
- s << "#{cond_indent_process(exp.shift)}"
324
- s << "else\n#{cond_indent_process(exp.shift)}" until exp.empty?
325
- s << "end"
326
- s.join("\n")
327
- end
328
-
329
- def process_iter(exp)
330
- owner = exp.shift
331
- args = exp.shift
332
- if !args.nil?
333
- @block_params = true
334
- end
335
- processed_args = process args
336
- block_args = processed_args.nil? ? "" : "|#{processed_args}|"
337
-
338
- result = "#{process owner} {#{block_args}\n" +
339
- indent("#{process exp.shift}\n") +
340
- "}"
341
- @block_params = false
342
- result
343
- end
344
-
345
- def process_ivar(exp)
346
- exp.shift.to_s
347
- end
348
-
349
- def process_lasgn(exp)
350
- s = "#{exp.shift}"
351
- s += " = #{process exp.shift}" unless exp.empty?
352
- s
353
- end
354
-
355
- def process_lit(exp)
356
- obj = exp.shift
357
- if obj.is_a? Range # to get around how parsed ranges turn into lits and lose parens
358
- "(" + obj.inspect + ")"
359
- else
360
- obj.inspect
361
- end
362
- end
363
-
364
- def process_lvar(exp)
365
- exp.shift.to_s
366
- end
367
-
368
- def process_masgn(exp)
369
- process(exp.shift)[1..-2]
370
- end
371
-
372
- def process_module(exp)
373
- s = "module #{exp.shift}\n"
374
- body = ""
375
- body << "#{process exp.shift}\n\n" until exp.empty?
376
- s + indent(body) + "end"
377
- end
378
-
379
- def process_nil(exp)
380
- "nil"
381
- end
382
-
383
- def process_not(exp)
384
- "(not #{process exp.shift})"
385
- end
386
-
387
- def process_or(exp)
388
- "(#{process exp.shift} or #{process exp.shift})"
389
- end
390
-
391
- def process_resbody(exp)
392
- s = "rescue "
393
- unless exp.empty?
394
- if exp.first.first == :array
395
- s << process(exp.shift)[1..-2]
396
- end
397
- s << "\n"
398
- end
399
- s << (process(exp.shift).to_s + "\n") until exp.empty?
400
- s
401
- end
402
-
403
- def process_rescue(exp)
404
- s = ""
405
- s << (process(exp.shift).to_s + "\n") until exp.empty?
406
- s
407
- end
408
-
409
- def process_retry(exp)
410
- "retry"
411
- end
412
-
413
- def process_return(exp)
414
- return "return #{process exp.shift}"
415
- end
416
-
417
- def process_scope(exp)
418
- return process(exp.shift)
419
- end
420
-
421
- def process_self(exp)
422
- "self"
423
- end
424
- def process_str(exp)
425
- return exp.shift.dump
426
- end
427
-
428
- def process_super(exp)
429
- "super(#{process(exp.shift)})"
430
- end
431
-
432
- def process_true(exp)
433
- "true"
434
- end
435
-
436
- def process_until(exp)
437
- cond_loop(exp, 'until')
438
- end
439
-
440
- def process_vcall(exp)
441
- return exp.shift.to_s
442
- end
443
-
444
- def process_when(exp)
445
- "when #{process(exp.shift).to_s[1..-2]}\n#{indent(process(exp.shift))}"
446
- end
447
-
448
- def process_while(exp)
449
- cond_loop(exp, 'while')
450
- end
451
-
452
- def process_yield(exp)
453
- body = process(exp.shift)[1..-2] unless exp.empty?
454
- "yield#{body and "(#{body})"}"
455
- end
456
-
457
- def process_zarray(exp)
458
- "[]"
459
- end
460
-
461
- def process_zsuper(exp)
462
- "super"
463
- end
464
-
465
- # def process_dxstr(exp)
466
- # puts "DXSTR:#{exp.shift}"
467
- # end
468
-
469
- def cond_loop(exp, name)
470
- cond = process(exp.shift)
471
- body = cond_indent_process(exp.shift)
472
- head_controlled = exp.empty? ? false : exp.shift
473
-
474
- code = []
475
- if head_controlled then
476
- code << "#{name} (#{cond}) do"
477
- code << body
478
- code << "end"
479
- else
480
- code << "begin"
481
- code << body
482
- code << "end #{name} (#{cond})"
483
- end
484
- code.join("\n")
485
- end
486
-
487
- def process_bmethod(exp)
488
- exp.clear
489
- ""
490
- end
491
-
492
- end