relevance-test-spec 0.4.0.5
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.
- data/CHANGELOG +1 -0
- data/Manifest +29 -0
- data/README.rdoc +394 -0
- data/ROADMAP +1 -0
- data/Rakefile +62 -0
- data/TODO +3 -0
- data/bin/specrb +107 -0
- data/examples/stack.rb +38 -0
- data/examples/stack_spec.rb +119 -0
- data/lib/test/spec.rb +731 -0
- data/lib/test/spec/dox.rb +148 -0
- data/lib/test/spec/focused/collector-extensions.rb +22 -0
- data/lib/test/spec/focused/focused.rb +30 -0
- data/lib/test/spec/rails_helper.rb +26 -0
- data/lib/test/spec/rdox.rb +25 -0
- data/lib/test/spec/should-output.rb +49 -0
- data/lib/test/spec/version.rb +8 -0
- data/test-spec.gemspec +130 -0
- data/test/helper.rb +5 -0
- data/test/spec_dox.rb +39 -0
- data/test/spec_flexmock.rb +214 -0
- data/test/spec_focused.rb +75 -0
- data/test/spec_mocha.rb +118 -0
- data/test/spec_nestedcontexts.rb +26 -0
- data/test/spec_new_style.rb +82 -0
- data/test/spec_should-output.rb +26 -0
- data/test/spec_testspec.rb +575 -0
- data/test/spec_testspec_order.rb +26 -0
- data/test/test_testunit.rb +22 -0
- metadata +127 -0
data/test/helper.rb
ADDED
data/test/spec_dox.rb
ADDED
@@ -0,0 +1,39 @@
|
|
1
|
+
require 'test/spec'
|
2
|
+
|
3
|
+
require 'test/spec/dox'
|
4
|
+
|
5
|
+
context "SpecDox" do
|
6
|
+
setup do
|
7
|
+
r = Test::Unit::UI::SpecDox::TestRunner.new(nil)
|
8
|
+
@unmangler = r.method(:unmangle)
|
9
|
+
end
|
10
|
+
|
11
|
+
specify "can unmangle Test::Unit names correctly" do
|
12
|
+
@unmangler["test_foo_bar(TestFoo)"].should.equal ["Foo", "foo bar"]
|
13
|
+
@unmangler["test_foo_bar(FooTest)"].should.equal ["Foo", "foo bar"]
|
14
|
+
@unmangler["test_he_he(Foo)"].should.equal ["Foo", "he he"]
|
15
|
+
@unmangler["test_heh(Foo)"].should.equal ["Foo", "heh"]
|
16
|
+
|
17
|
+
@unmangler["test_heh(Test::Unit::TC_Assertions)"].
|
18
|
+
should.equal ["Test::Unit::TC_Assertions", "heh"]
|
19
|
+
|
20
|
+
@unmangler["test_heh(Foo::Bar::Test)"].
|
21
|
+
should.equal ["Foo::Bar::Test", "heh"]
|
22
|
+
end
|
23
|
+
|
24
|
+
specify "can unmangle Test::Spec names correctly" do
|
25
|
+
@unmangler["test_spec {context} 007 [whee]()"].
|
26
|
+
should.equal ["context", "whee"]
|
27
|
+
@unmangler["test_spec {a bit longish context} 069 [and more text]()"].
|
28
|
+
should.equal ["a bit longish context", "and more text"]
|
29
|
+
@unmangler["test_spec {special chars !\"/&%$} 2 [special chars !\"/&%$]()"].
|
30
|
+
should.equal ["special chars !\"/&%$", "special chars !\"/&%$"]
|
31
|
+
@unmangler["test_spec {[]} 666666 [{}]()"].
|
32
|
+
should.equal ["[]", "{}"]
|
33
|
+
end
|
34
|
+
|
35
|
+
specify "has sensible fallbacks" do
|
36
|
+
@unmangler["weird"].should.equal [nil, nil]
|
37
|
+
end
|
38
|
+
end
|
39
|
+
|
@@ -0,0 +1,214 @@
|
|
1
|
+
# Adapted from flexmock (http://onestepback.org/software/flexmock).
|
2
|
+
#
|
3
|
+
# Copyright 2006 by Jim Weirich (jweirich@one.net).
|
4
|
+
# All rights reserved.
|
5
|
+
|
6
|
+
# Permission is granted for use, copying, modification, distribution,
|
7
|
+
# and distribution of modified versions of this work as long as the
|
8
|
+
# above copyright notice is included.
|
9
|
+
|
10
|
+
|
11
|
+
require 'test/spec'
|
12
|
+
|
13
|
+
begin
|
14
|
+
require 'flexmock'
|
15
|
+
rescue LoadError
|
16
|
+
context "flexmock" do
|
17
|
+
specify "can not be found. BAIL OUT!" do
|
18
|
+
end
|
19
|
+
end
|
20
|
+
else
|
21
|
+
|
22
|
+
context "flexmock" do
|
23
|
+
include FlexMock::TestCase
|
24
|
+
|
25
|
+
setup do
|
26
|
+
@mock = FlexMock.new
|
27
|
+
end
|
28
|
+
|
29
|
+
specify "should handle" do
|
30
|
+
args = nil
|
31
|
+
@mock.mock_handle(:hi) { |a, b| args = [a,b] }
|
32
|
+
@mock.hi(1,2)
|
33
|
+
args.should.equal [1,2]
|
34
|
+
end
|
35
|
+
|
36
|
+
specify "should handle without a block" do
|
37
|
+
lambda {
|
38
|
+
@mock.mock_handle(:blip)
|
39
|
+
@mock.blip
|
40
|
+
}.should.not.raise
|
41
|
+
end
|
42
|
+
|
43
|
+
specify "should handle with a block" do
|
44
|
+
called = false
|
45
|
+
@mock.mock_handle(:blip) { |block| block.call }
|
46
|
+
@mock.blip { called = true }
|
47
|
+
called.should.be true
|
48
|
+
end
|
49
|
+
|
50
|
+
specify "should have a return value" do
|
51
|
+
@mock.mock_handle(:blip) { 10 }
|
52
|
+
@mock.blip.should.equal 10
|
53
|
+
end
|
54
|
+
|
55
|
+
specify "should handle missing methods" do
|
56
|
+
ex = lambda {
|
57
|
+
@mock.not_defined
|
58
|
+
}.should.raise(NoMethodError)
|
59
|
+
ex.message.should.match(/not_defined/)
|
60
|
+
end
|
61
|
+
|
62
|
+
specify "should ignore missing methods" do
|
63
|
+
lambda {
|
64
|
+
@mock.mock_ignore_missing
|
65
|
+
@mock.blip
|
66
|
+
}.should.not.raise
|
67
|
+
end
|
68
|
+
|
69
|
+
specify "should count correctly" do
|
70
|
+
@mock.mock_handle(:blip, 3)
|
71
|
+
@mock.blip
|
72
|
+
@mock.blip
|
73
|
+
@mock.blip
|
74
|
+
lambda { @mock.mock_verify }.should.not.raise Test::Unit::AssertionFailedError
|
75
|
+
end
|
76
|
+
|
77
|
+
specify "should raise on bad counts" do
|
78
|
+
@mock.mock_handle(:blip, 3)
|
79
|
+
@mock.blip
|
80
|
+
@mock.blip
|
81
|
+
lambda { @mock.mock_verify }.should.raise Test::Unit::AssertionFailedError
|
82
|
+
end
|
83
|
+
|
84
|
+
specify "should handle undetermined counts" do
|
85
|
+
lambda {
|
86
|
+
FlexMock.use('fs') { |m|
|
87
|
+
m.mock_handle(:blip)
|
88
|
+
m.blip
|
89
|
+
m.blip
|
90
|
+
m.blip
|
91
|
+
}
|
92
|
+
}.should.not.raise Test::Unit::AssertionFailedError
|
93
|
+
end
|
94
|
+
|
95
|
+
specify "should handle zero counts" do
|
96
|
+
lambda {
|
97
|
+
FlexMock.use { |m|
|
98
|
+
m.mock_handle(:blip, 0)
|
99
|
+
m.blip
|
100
|
+
}
|
101
|
+
}.should.raise Test::Unit::AssertionFailedError
|
102
|
+
end
|
103
|
+
|
104
|
+
specify "should have file IO with use" do
|
105
|
+
file = FlexMock.use do |m|
|
106
|
+
filedata = ["line 1", "line 2"]
|
107
|
+
m.mock_handle(:gets, 3) { filedata.shift }
|
108
|
+
count_lines(m).should.equal 2
|
109
|
+
end
|
110
|
+
end
|
111
|
+
|
112
|
+
def count_lines(stream)
|
113
|
+
result = 0
|
114
|
+
while line = stream.gets
|
115
|
+
result += 1
|
116
|
+
end
|
117
|
+
result
|
118
|
+
end
|
119
|
+
|
120
|
+
specify "should have use" do
|
121
|
+
lambda {
|
122
|
+
FlexMock.use do |m|
|
123
|
+
m.mock_handle(:blip, 2)
|
124
|
+
m.blip
|
125
|
+
end
|
126
|
+
}.should.raise Test::Unit::AssertionFailedError
|
127
|
+
end
|
128
|
+
|
129
|
+
specify "should handle failures during use" do
|
130
|
+
ex = lambda {
|
131
|
+
FlexMock.use do |m|
|
132
|
+
m.mock_handle(:blip, 2)
|
133
|
+
xyz
|
134
|
+
end
|
135
|
+
}.should.raise NameError
|
136
|
+
ex.message.should.match(/undefined local variable or method/)
|
137
|
+
end
|
138
|
+
|
139
|
+
specify "should deal with sequential values" do
|
140
|
+
values = [1,4,9,16]
|
141
|
+
@mock.mock_handle(:get) { values.shift }
|
142
|
+
@mock.get.should.equal 1
|
143
|
+
@mock.get.should.equal 4
|
144
|
+
@mock.get.should.equal 9
|
145
|
+
@mock.get.should.equal 16
|
146
|
+
end
|
147
|
+
|
148
|
+
specify "respond_to? should return false for non handled methods" do
|
149
|
+
@mock.should.not.respond_to :blah
|
150
|
+
end
|
151
|
+
|
152
|
+
specify "respond_to? should return true for explicit methods" do
|
153
|
+
@mock.mock_handle(:xyz)
|
154
|
+
@mock.should.respond_to :xyz
|
155
|
+
end
|
156
|
+
|
157
|
+
specify "respond_to? should return true when ignoring_missing" do
|
158
|
+
@mock.mock_ignore_missing
|
159
|
+
@mock.should.respond_to :yada
|
160
|
+
end
|
161
|
+
|
162
|
+
specify "respond_to? should return true for missing_methods when should_ignore_missing" do
|
163
|
+
@mock.should_ignore_missing
|
164
|
+
@mock.should.respond_to :yada
|
165
|
+
end
|
166
|
+
|
167
|
+
specify "should raise error on unknown method proc" do
|
168
|
+
lambda {
|
169
|
+
@mock.method(:xyzzy)
|
170
|
+
}.should.raise NameError
|
171
|
+
end
|
172
|
+
|
173
|
+
specify "should return callable proc on method" do
|
174
|
+
got_it = false
|
175
|
+
@mock.mock_handle(:xyzzy) { got_it = true }
|
176
|
+
method_proc = @mock.method(:xyzzy)
|
177
|
+
method_proc.should.not.be.nil
|
178
|
+
method_proc.call
|
179
|
+
got_it.should.be true
|
180
|
+
end
|
181
|
+
|
182
|
+
specify "should return do nothing proc for missing methods" do
|
183
|
+
@mock.mock_ignore_missing
|
184
|
+
method_proc = @mock.method(:plugh)
|
185
|
+
method_proc.should.not.be.nil
|
186
|
+
lambda { method_proc.call }.should.not.raise
|
187
|
+
end
|
188
|
+
end
|
189
|
+
|
190
|
+
|
191
|
+
class TemperatureSampler
|
192
|
+
def initialize(sensor)
|
193
|
+
@sensor = sensor
|
194
|
+
end
|
195
|
+
|
196
|
+
def average_temp
|
197
|
+
total = (0...3).collect { @sensor.read_temperature }.inject { |i, s| i + s }
|
198
|
+
total / 3.0
|
199
|
+
end
|
200
|
+
end
|
201
|
+
|
202
|
+
context "flexmock" do
|
203
|
+
include FlexMock::TestCase
|
204
|
+
|
205
|
+
specify "works with test/spec" do
|
206
|
+
sensor = flexmock("temp")
|
207
|
+
sensor.should_receive(:read_temperature).times(3).and_return(10, 12, 14)
|
208
|
+
|
209
|
+
sampler = TemperatureSampler.new(sensor)
|
210
|
+
sampler.average_temp.should.equal 12
|
211
|
+
end
|
212
|
+
end
|
213
|
+
|
214
|
+
end # if not rescue LoadError
|
@@ -0,0 +1,75 @@
|
|
1
|
+
require File.expand_path(File.join(File.dirname(__FILE__), *%w[helper]))
|
2
|
+
|
3
|
+
describe "focused methods" do
|
4
|
+
it "context methods are extended on to the test case" do
|
5
|
+
spec = Test::Spec::TestCase.new('stub')
|
6
|
+
spec.testcase.should.respond_to :fcontext
|
7
|
+
spec.testcase.should.respond_to :fdescribe
|
8
|
+
end
|
9
|
+
|
10
|
+
it "spec methods are extended on to the test case" do
|
11
|
+
spec = Test::Spec::TestCase.new('stub')
|
12
|
+
spec.testcase.should.respond_to :fspecify
|
13
|
+
spec.testcase.should.respond_to :fit
|
14
|
+
end
|
15
|
+
|
16
|
+
end
|
17
|
+
|
18
|
+
describe "turning on focused mode" do
|
19
|
+
teardown do
|
20
|
+
Test::Spec::CONTEXTS.map { |k, v| v.ignore = false }
|
21
|
+
end
|
22
|
+
|
23
|
+
it "sets ignore on all previous contexts" do
|
24
|
+
Kernel.module_eval do
|
25
|
+
describe("first context") { it("should never run") { assert 1 == 2 } }
|
26
|
+
fcontext("second context") { it("focuses on this spec") { assert 1 == 1} }
|
27
|
+
end
|
28
|
+
|
29
|
+
Test::Spec::CONTEXTS["first context"].ignore?.should == true
|
30
|
+
Test::Spec::CONTEXTS["second context"].ignore?.should == false
|
31
|
+
end
|
32
|
+
|
33
|
+
it "sets ignore on all previous specs" do
|
34
|
+
Kernel.module_eval do
|
35
|
+
describe("first context") { it("should never run") { assert 1 == 2 } }
|
36
|
+
context("second context") {
|
37
|
+
it("this should be undefed") { raise }
|
38
|
+
fit("focuses on this spec") { assert 1 == 1} }
|
39
|
+
end
|
40
|
+
Test::Spec::CONTEXTS["first context"].ignore?.should == true
|
41
|
+
Test::Spec::CONTEXTS["second context"].ignore?.should == false
|
42
|
+
end
|
43
|
+
|
44
|
+
it "undefs previous spec methods when focusing on a spec" do
|
45
|
+
Kernel.module_eval do
|
46
|
+
context("my context") {
|
47
|
+
it("this should be undefed") { raise }
|
48
|
+
fit("focuses on this spec") { assert 1 == 1} }
|
49
|
+
end
|
50
|
+
Test::Spec::CONTEXTS["my context"].testcase.instance_methods.grep(/test_spec/).size.should == 1
|
51
|
+
end
|
52
|
+
|
53
|
+
end
|
54
|
+
|
55
|
+
describe "focused context/describe blocks" do
|
56
|
+
setup do
|
57
|
+
@spec = Test::Spec::TestCase.new('stub')
|
58
|
+
end
|
59
|
+
|
60
|
+
it "turns on focused mode for top level contexts" do
|
61
|
+
Test::Spec.expects(:set_focused_mode).with(true).once
|
62
|
+
Kernel.fcontext("stub context") { "foo" }
|
63
|
+
end
|
64
|
+
|
65
|
+
it "turns on focused mode for nested contexts" do
|
66
|
+
Test::Spec.expects(:set_focused_mode).with(true).once
|
67
|
+
@spec.testcase.fcontext("stub context") { "foo" }
|
68
|
+
end
|
69
|
+
|
70
|
+
it "sets all previous contexts to disabled" do
|
71
|
+
Test::Spec.expects(:ignore_previous_specs)
|
72
|
+
@spec.testcase.fcontext("stub context") { "foo" }
|
73
|
+
end
|
74
|
+
|
75
|
+
end
|
data/test/spec_mocha.rb
ADDED
@@ -0,0 +1,118 @@
|
|
1
|
+
# Adapted from mocha (http://mocha.rubyforge.org/).
|
2
|
+
#
|
3
|
+
# Copyright (C) 2006 Revieworld Ltd.
|
4
|
+
#
|
5
|
+
# You may use, copy and redistribute this library under the same terms
|
6
|
+
# as Ruby itself (see www.ruby-lang.org/en/LICENSE.txt) or under the
|
7
|
+
# MIT license (see MIT-LICENSE file).
|
8
|
+
|
9
|
+
require 'test/spec'
|
10
|
+
|
11
|
+
$: << "/home/chris/src/mocha-0.3.2/lib"
|
12
|
+
|
13
|
+
begin
|
14
|
+
require 'mocha'
|
15
|
+
rescue LoadError
|
16
|
+
context "mocha" do
|
17
|
+
specify "can not be found. BAIL OUT!" do
|
18
|
+
end
|
19
|
+
end
|
20
|
+
else
|
21
|
+
|
22
|
+
context "mocha" do
|
23
|
+
specify "works with test/spec" do
|
24
|
+
object = mock()
|
25
|
+
object.expects(:expected_method).with(:p1, :p2).returns(:result)
|
26
|
+
object.expected_method(:p1, :p2).should.equal :result
|
27
|
+
end
|
28
|
+
end
|
29
|
+
|
30
|
+
class Enterprise
|
31
|
+
def initialize(dilithium)
|
32
|
+
@dilithium = dilithium
|
33
|
+
end
|
34
|
+
|
35
|
+
def go(warp_factor)
|
36
|
+
warp_factor.times { @dilithium.nuke(:anti_matter) }
|
37
|
+
end
|
38
|
+
end
|
39
|
+
|
40
|
+
context "mocha" do
|
41
|
+
specify "works with test/spec and Enterprise example" do
|
42
|
+
dilithium = mock()
|
43
|
+
dilithium.expects(:nuke).with(:anti_matter).at_least_once # auto-verified at end of test
|
44
|
+
enterprise = Enterprise.new(dilithium)
|
45
|
+
enterprise.go(2)
|
46
|
+
end
|
47
|
+
end
|
48
|
+
|
49
|
+
end # if not rescue LoadError
|
50
|
+
|
51
|
+
|
52
|
+
begin
|
53
|
+
require 'mocha'
|
54
|
+
rescue LoadError
|
55
|
+
context "mocha" do
|
56
|
+
specify "can not be found. BAIL OUT!" do
|
57
|
+
end
|
58
|
+
end
|
59
|
+
else
|
60
|
+
|
61
|
+
class Order
|
62
|
+
attr_accessor :shipped_on
|
63
|
+
|
64
|
+
def total_cost
|
65
|
+
line_items.inject(0) { |total, line_item| total + line_item.price } + shipping_cost
|
66
|
+
end
|
67
|
+
|
68
|
+
def total_weight
|
69
|
+
line_items.inject(0) { |total, line_item| total + line_item.weight }
|
70
|
+
end
|
71
|
+
|
72
|
+
def shipping_cost
|
73
|
+
total_weight * 5 + 10
|
74
|
+
end
|
75
|
+
|
76
|
+
class << self
|
77
|
+
|
78
|
+
def find_all
|
79
|
+
# Database.connection.execute('select * from orders...
|
80
|
+
end
|
81
|
+
|
82
|
+
def number_shipped_since(date)
|
83
|
+
find_all.select { |order| order.shipped_on > date }.size
|
84
|
+
end
|
85
|
+
|
86
|
+
def unshipped_value
|
87
|
+
find_all.inject(0) { |total, order| order.shipped_on ? total : total + order.total_cost }
|
88
|
+
end
|
89
|
+
|
90
|
+
end
|
91
|
+
|
92
|
+
end
|
93
|
+
|
94
|
+
context "mocha" do
|
95
|
+
specify "works with test/spec and instance method stubbing" do
|
96
|
+
order = Order.new
|
97
|
+
order.stubs(:total_weight).returns(10)
|
98
|
+
order.shipping_cost.should.equal 60
|
99
|
+
end
|
100
|
+
|
101
|
+
specify "works with test/spec and class method stubbing" do
|
102
|
+
now = Time.now; week_in_secs = 7 * 24 * 60 * 60
|
103
|
+
order_1 = Order.new; order_1.shipped_on = now - 1 * week_in_secs
|
104
|
+
order_2 = Order.new; order_2.shipped_on = now - 3 * week_in_secs
|
105
|
+
Order.stubs(:find_all).returns([order_1, order_2])
|
106
|
+
Order.number_shipped_since(now - 2 * week_in_secs).should.equal 1
|
107
|
+
end
|
108
|
+
|
109
|
+
specify "works with test/spec and global instance method stubbing" do
|
110
|
+
Order.stubs(:find_all).returns([Order.new, Order.new, Order.new])
|
111
|
+
Order.any_instance.stubs(:shipped_on).returns(nil)
|
112
|
+
Order.any_instance.stubs(:total_cost).returns(10)
|
113
|
+
Order.unshipped_value.should.equal 30
|
114
|
+
end
|
115
|
+
end
|
116
|
+
|
117
|
+
end # if not rescue LoadError
|
118
|
+
|