baretest 0.1.0 → 0.2.3

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 (69) hide show
  1. data/LICENSE.txt +52 -0
  2. data/MANIFEST.txt +50 -31
  3. data/README.rdoc +260 -0
  4. data/bin/baretest +82 -24
  5. data/doc/baretest.rdoc +98 -0
  6. data/doc/mocking_stubbing_test_doubles.rdoc +5 -0
  7. data/doc/quickref.rdoc +261 -0
  8. data/doc/writing_tests.rdoc +148 -0
  9. data/examples/test.rake +58 -30
  10. data/examples/tests/irb_mode/failures.rb +26 -0
  11. data/examples/tests/mock_developer/test/helper/mocks.rb +0 -0
  12. data/examples/tests/mock_developer/test/setup.rb +57 -0
  13. data/examples/tests/mock_developer/test/suite/mock_demo.rb +19 -0
  14. data/examples/tests/overview/test.rb +89 -0
  15. data/examples/tests/variations/variations_01.rb +14 -0
  16. data/examples/tests/variations/variations_02.rb +19 -0
  17. data/examples/tests/variations/variations_03.rb +19 -0
  18. data/lib/baretest/assertion/context.rb +20 -0
  19. data/lib/baretest/assertion/failure.rb +22 -0
  20. data/lib/baretest/assertion/skip.rb +21 -0
  21. data/lib/{test → baretest}/assertion/support.rb +174 -39
  22. data/lib/baretest/assertion.rb +182 -0
  23. data/lib/baretest/irb_mode.rb +263 -0
  24. data/lib/{test/assertion/failure.rb → baretest/layout.rb} +6 -5
  25. data/lib/baretest/mocha.rb +18 -0
  26. data/lib/baretest/run/cli.rb +104 -0
  27. data/lib/{test → baretest}/run/errors.rb +12 -7
  28. data/lib/{test → baretest}/run/minimal.rb +8 -3
  29. data/lib/baretest/run/profile.rb +151 -0
  30. data/lib/{test → baretest}/run/spec.rb +10 -4
  31. data/lib/baretest/run/tap.rb +44 -0
  32. data/lib/baretest/run/xml.rb +80 -0
  33. data/lib/{test → baretest}/run.rb +31 -18
  34. data/lib/baretest/setup.rb +15 -0
  35. data/lib/baretest/skipped/assertion.rb +20 -0
  36. data/lib/baretest/skipped/suite.rb +49 -0
  37. data/lib/baretest/skipped.rb +15 -0
  38. data/lib/baretest/suite.rb +234 -0
  39. data/lib/baretest/utilities.rb +43 -0
  40. data/lib/{test → baretest}/version.rb +12 -3
  41. data/lib/baretest.rb +112 -0
  42. data/test/external/bootstraptest.rb +1 -1
  43. data/test/setup.rb +1 -1
  44. data/test/{lib/test → suite/lib/baretest}/assertion/support.rb +78 -24
  45. data/test/suite/lib/baretest/assertion.rb +192 -0
  46. data/test/{lib/test → suite/lib/baretest}/irb_mode.rb +0 -0
  47. data/test/{lib/test → suite/lib/baretest}/run/cli.rb +0 -0
  48. data/test/{lib/test → suite/lib/baretest}/run/errors.rb +0 -0
  49. data/test/{lib/test → suite/lib/baretest}/run/interactive.rb +0 -0
  50. data/test/{lib/test → suite/lib/baretest}/run/spec.rb +0 -0
  51. data/test/{lib/test → suite/lib/baretest}/run/tap.rb +0 -0
  52. data/test/{lib/test → suite/lib/baretest}/run/xml.rb +0 -0
  53. data/test/{lib/test → suite/lib/baretest}/run.rb +63 -61
  54. data/test/{lib/test → suite/lib/baretest}/suite.rb +77 -54
  55. data/test/{lib/test.rb → suite/lib/baretest.rb} +37 -37
  56. metadata +61 -40
  57. data/README.markdown +0 -229
  58. data/examples/test.rb +0 -93
  59. data/lib/test/assertion.rb +0 -117
  60. data/lib/test/debug.rb +0 -34
  61. data/lib/test/irb_mode.rb +0 -104
  62. data/lib/test/run/cli.rb +0 -79
  63. data/lib/test/run/interactive.rb +0 -60
  64. data/lib/test/run/tap.rb +0 -32
  65. data/lib/test/run/xml.rb +0 -56
  66. data/lib/test/suite.rb +0 -95
  67. data/lib/test.rb +0 -118
  68. data/test/lib/test/assertion.rb +0 -142
  69. data/test/lib/test/debug.rb +0 -63
data/doc/quickref.rdoc ADDED
@@ -0,0 +1,261 @@
1
+ = BareTest Quick Reference
2
+
3
+ This is a very condensed overview over baretest. If you're new to testing and
4
+ new to baretest, you may be more interested into doc/writing_tests.rdoc
5
+ Also look into the examples and baretests own test directory.
6
+
7
+
8
+
9
+ == Setup baretest
10
+
11
+ 1. Install baretest
12
+ a) official release: `sudo gem install baretest`
13
+ b) edge:
14
+ 1. git clone git://github.com/apeiros/baretest.git
15
+ 2. cd baretest
16
+ 3. rake gem:install
17
+ 2. Change into the project directory
18
+ 3. `baretest --init` to create the basic test-directory layout
19
+
20
+
21
+
22
+ == Location of testfiles
23
+
24
+ Your tests for PROJECT/lib/foo.rb belong into PROJECT/test/suite/lib/foo.rb.
25
+ Your tests for PROJECT/bin/bar belong into PROJECT/test/suite/bin/bar.
26
+ In other words, for every path, insert /test/suite after PROJECT to get the
27
+ path to the corresponding testfile.
28
+
29
+
30
+
31
+ == Writing tests
32
+
33
+ A testfile commonly looks like this:
34
+
35
+ BareTest.suite "module ModuleName" do
36
+ setup do
37
+ # This is run before each assert, that is in this suite or a nested suite
38
+ end
39
+
40
+ teardown do
41
+ # This is run after each assert, that is in this suite or a nested suite
42
+ end
43
+
44
+ suite "Class methods" do
45
+ setup do
46
+ # things used by most nested suites
47
+ end
48
+
49
+ suite "ModuleName::class_method_name" do
50
+ assert "does this" do
51
+ ...
52
+ end
53
+
54
+ assert "does that" do
55
+ end
56
+ end
57
+
58
+ suite "Instance methods" do
59
+ suite "ModuleName#instance_method_name" do
60
+ ...
61
+ end
62
+ end
63
+
64
+ suite "class ClassName" do # this is class ModuleName::ClassName
65
+ suite "Class methods" do
66
+ ...
67
+ end
68
+
69
+ suite "Instance methods" do
70
+ ...
71
+ end
72
+ end
73
+ end
74
+
75
+ This layout makes it easy to figure where tests for something are, and thus
76
+ makes maintaining the test-code base easier.
77
+
78
+ Setup callbacks are invoked from outermost suite to innermost suite, and
79
+ within the same suite, in the order of definition.
80
+
81
+ Teardown callbacks are invoked from innermost suite to outermost suite, and
82
+ within the same suite, in the order of definition.
83
+
84
+ BareTest.suite do
85
+ setup do puts 1 end
86
+ setup do puts 2 end
87
+ teardown do puts 7 end
88
+ teardown do puts 8 end
89
+
90
+ suite "Inner" do
91
+ setup do puts 3 end
92
+ setup do puts 4 end
93
+ teardown do puts 5 end
94
+ teardown do puts 6 end
95
+
96
+ assert "Inner - assert" do puts "Inner - assert" end
97
+ end
98
+
99
+ assert "Outer - assert" do puts "Outer - assert" end
100
+ end
101
+
102
+ Running this suite will print:
103
+
104
+ 1
105
+ 2
106
+ 3
107
+ 4
108
+ Inner - assert
109
+ 5
110
+ 6
111
+ 7
112
+ 8
113
+ 1
114
+ 2
115
+ Outer - assert
116
+ 7
117
+ 8
118
+
119
+
120
+
121
+ == Skipping Tests and Suites
122
+
123
+ A test is skipped if it does not have a block or calls 'skip'
124
+
125
+ == Assertion helper methods
126
+
127
+ See BareTest::Assertion::Support
128
+ All methods that have the method signature foo(expected, actual, message=nil)
129
+ can alternatively be used with named arguments:
130
+ foo a, b, "message" # is equivalent to:
131
+ foo :expected => a, :actual => b, :message => "message"
132
+
133
+ * skip(message, *args)
134
+ Description: Skips the assertion, uses sprintf with message and *args
135
+ Success: not possible
136
+ Failure: not possible
137
+
138
+ * failure(message, *args)
139
+ Description: Lets the assertion fail, uses sprintf with message and *args
140
+ Success: not possible
141
+ Failure: failure("%p was not the inverse of %p", 2, 5)
142
+
143
+ * same(expected, actual, message=nil)
144
+ Description: Uses expected.equal?(actual), which tests for object identity
145
+ Success: same(:foo, :foo)
146
+ Failure: same("foo", "foo")
147
+
148
+ * hash_key_equal(expected, actual, message=nil)
149
+ Description: Uses expected.eql?(actual), which is used for hash key equality.
150
+ Success: hash_key_equal("foo", "foo")
151
+ Failure: hash_key_equal(1.0, 1)
152
+
153
+ * equal(expected, actual, message=nil) (alias: order_equal)
154
+ Description: Uses expected == actual, which is used for order-equality.
155
+ Success: equal(1.0, 1)
156
+ Failure: equal(1, "1")
157
+
158
+ * case_equal(expected, actual, message=nil)
159
+ Description: Uses expected === actual, which is used in case/whens.
160
+ Success: case_equal(String, "foo")
161
+ Failure: case_equal(String, 1)
162
+
163
+ * equal_unordered(expected, actual, message=nil)
164
+ Description: Compares unordered enumerables, on the enumerable it uses each,
165
+ on the items it uses hash and eql?
166
+ Success: equal_unordered([1,2], [2,1])
167
+ Failure: equal_unordered([1,2], [2,1,2])
168
+
169
+ * within_delta(a, b, delta)
170
+ Description: Tests whether the difference between a and b is less than delta
171
+ Success: within_delta(0.5, Math.sin(Math::PI/6), 1e-6)
172
+ # equal(0.5, Math.sin(Math::PI/6)) would fail
173
+ Failure: within_delta(0.5, 0.6, 0.05)
174
+
175
+ * kind_of(expected, actual, message=nil) (alias: is_a)
176
+ Description: Uses actual.kind_of?(expected)
177
+ Success: kind_of(String, "foo")
178
+ Failure: kind_of(String, 1)
179
+
180
+ * throws(symbol)
181
+ Description: Test whether the block throws the given symbol
182
+ Success: throws(:foo) do throw(:foo) end
183
+ Failure: throws(:foo) do throw(:bar) end
184
+ throws(:foo) do nil end
185
+
186
+ * throws_nothing
187
+ Description: Test whether a piece of code really throws nothing
188
+ Success: throws_nothing do nil end
189
+ Failure: throws_nothing do throw(:foo) end
190
+
191
+ * raises(exception_class=StandardError, opts={})
192
+ Description: Test whether the block raises
193
+ Success: raises do raise "foo" end
194
+ raises ArgumentError do "12".to_i(10, :superfluous) end
195
+ Failure: raises do nil end
196
+ raises ArgumentError do "12".to_i(10) end
197
+
198
+ * raises_nothing
199
+ Description: Test whether the block doesn't raise
200
+ Success: raise_nothing do nil end
201
+ Failure: raise_nothing do raise "foo" end
202
+
203
+ * touch(thing=nil)
204
+ Description: Mark reaching a point in code, e.g. that a block was invoked
205
+ Success: -> see touched
206
+ Failure: -> see touched
207
+
208
+ * touched(thing=nil, times=nil)
209
+ Description: test whether a mark for reached code was set, optionally test
210
+ whether it was set the expected number of times
211
+ Success: touch; touched
212
+ touch :thing; touched :thing
213
+ touch :thing; touch :thing; touched :thing, 2
214
+ Failure: touched
215
+ touch :thing; touched :something
216
+ touch :thing; touched :thing, 2
217
+
218
+ * not_touched(thing=nil)
219
+ Description: same as touched(thing, 0)
220
+ Success: see touched
221
+ Failure: see touched
222
+
223
+
224
+
225
+ == Running tests
226
+
227
+ baretest's test-cycle is:
228
+
229
+ 1. Create Run instance and the toplevel suite
230
+ 2. Load everything as required by the command line flags
231
+ 3. Load PROJECT/test/setup.rb
232
+ 4. Find PROJECT/test/suite/**/*.rb
233
+ 5. Load each file found in 2., but for every file, see whether
234
+ PROJECT/test/helpers/suite/**/*.rb exists and load that first if it does
235
+ 6. Invoke run on the Run instance
236
+
237
+ From there on it depends on the loaded formatters and extenders, what really
238
+ will happen. But the norm is, that suites and assertions will be executed in
239
+ order of definition.
240
+
241
+
242
+
243
+ == Debugging tests
244
+
245
+ Use `baretest -i` to run baretest in interactive mode. When a failure or an
246
+ error occurs, you have access to the following commands:
247
+
248
+ * s! - original assertions' status
249
+ * e! - error message and full backtrace
250
+ * em! - error message
251
+ * bt! - full backtrace
252
+ * iv! - all available instance variables
253
+ * cv! - all available class variables
254
+ * gv! - all available global variables
255
+ * file - file this assertion was defined in
256
+ * line - line number in the file where this assertion's definition starts
257
+ * nesting - a '>'-separated list of suite descriptions this assertion is
258
+ nested in
259
+ * description - this assertion's description
260
+ * code - code of this assertion
261
+ * help - overview over all the commands
@@ -0,0 +1,148 @@
1
+ = Writing Tests
2
+
3
+
4
+
5
+ This tutorial assumes you have basic ruby knowledge. It is an introduction into
6
+ baretest and testing itself.
7
+ If you're a quick study and have already good knowledge about ruby and testing,
8
+ you may be more interested in just reading the examples and the
9
+ doc/quickref.rdoc.
10
+
11
+
12
+
13
+ == 1. In the beginning there was the project
14
+
15
+ The first step is of course the project. Baretest was written with the
16
+ assumption of a standard ruby project layout (should work fine without too,
17
+ though - might just require a bit more work on your part).
18
+ The standard directory layout looks like this:
19
+
20
+ |-- bin (executables)
21
+ |-- doc (additional documentation)
22
+ |-- ext (native extension code will be here)
23
+ |-- examples (for the users of the lib)
24
+ |-- lib (contains the library)
25
+ |-- rake (contains rake relevant stuff)
26
+ `-- Rakefile
27
+
28
+ In your project directory, you can invoke `baretest --init`, this will
29
+ create the 'test' directory. It will mirror your project directory. That is,
30
+ it will recreate all directories nested in bin and lib within test/suite.
31
+ The directory layout of 'test' is as follows:
32
+
33
+ `-- test
34
+ |-- external (baretest ignores this directory)
35
+ |-- helper (baretest loads helper/lib/foo.rb when loading suite/lib/foo.rb)
36
+ |-- setup.rb (setup.rb is loaded as the first file when running baretest)
37
+ `-- suite (in here are the tests itself)
38
+ |-- bin (the tests for bin, PROJECT/bin is replicated here)
39
+ `-- lib (the tests for lib, PROJECT/lib is replicated here)
40
+
41
+
42
+
43
+ == 2. Writing the tests
44
+
45
+ Assume you have `lib/foo.rb` containing the class 'Foo'. To test it, you create
46
+ the file `test/suite/lib/foo.rb`. You start out by creating a suite for your
47
+ class:
48
+
49
+ BareTest.suite "class Foo" do
50
+ end
51
+
52
+ You're in no way limited in how you name the suites. It's an arbitrary String.
53
+ Now lets assume 'lib/foo.rb' contains the following code:
54
+
55
+ class Foo
56
+ def bar
57
+ "bar"
58
+ end
59
+ end
60
+
61
+ Then follows the next step, we write the first assertion:
62
+
63
+ BareTest.suite do
64
+ suite "class Foo" do
65
+ assert "bar returns 'bar'" do
66
+ Foo.new.bar == 'bar'
67
+ end
68
+ end
69
+ end
70
+
71
+ As you can see, the assertion is plain ruby code. The return value of the block
72
+ decides whether the assertion is considered a success (trueish value, that is
73
+ all but false and nil) or a failure (falseish value, that is false or nil).
74
+
75
+
76
+
77
+ == 3. Running the tests
78
+
79
+ First you change the directory to your project's root directory.
80
+ There you run `baretest`. That's it.
81
+ Baretest will now load the 'test/setup.rb' file, then it'll search in
82
+ 'test/suite' for files and find 'test/suite/lib/foo.rb'. Before loading that
83
+ file, it'll see if there's also a file 'test/helpers/suite/lib/foo.rb'. If
84
+ there was, it'd load that first. After that, it loads the
85
+ 'test/suite/lib/foo.rb' file. When all testfiles are discovered and loaded,
86
+ it'll run the tests.
87
+
88
+
89
+
90
+ == 4. Separating parts of the test
91
+
92
+ A classical test consists of four phases:
93
+
94
+ 1. setup
95
+ 2. exercise
96
+ 3. validate
97
+ 4. teardown
98
+
99
+ Baretest has setup and teardown on suites, which will be run for every assertion
100
+ the suite contains.
101
+ Exercise and validate is currently combined in the 'assert' method.
102
+
103
+ So let's make use of that and rewrite our previous test:
104
+
105
+ BareTest.suite do
106
+ suite "class Foo" do
107
+ setup do
108
+ @foo = Foo.new
109
+ end
110
+
111
+ assert "bar returns 'bar'" do
112
+ @foo.bar == 'bar'
113
+ end
114
+ end
115
+ end
116
+
117
+ In this simplistic example, this may seem like wasted time. The more complex the
118
+ setup becomes and the more assertions need the same setup, the more time a
119
+ separate setup phase saves.
120
+ It additionally helps in making intent clear: this is setup, and this is test.
121
+
122
+
123
+ == 5. When troubles strike
124
+
125
+ If one of your assertions fails or errors, you can use `baretest -i` to
126
+ investigate the issue. It will throw you into an irb session, with
127
+ self being the failing/erroring assertion and with several helpful
128
+ methods (use `help` in the irb session to get a list of those).
129
+
130
+ == Things left to be written out
131
+ * toplevel suite may have a name/description too, it'll act the same as if
132
+ there was a suite in an unnamed toplevel suite
133
+ * [setup] They will also be run for every nested suite's assertion,
134
+ where the outermost setup is run first, the innermost last.
135
+ * using stubs & mocks
136
+ * However, suites with the same name are considered the same.
137
+
138
+ For example, this code:
139
+
140
+ BareTest.suite "class Foo" do
141
+ suite "class Bar" do
142
+ assert "foo"
143
+ end
144
+
145
+
146
+ Just like ruby's
147
+ namespacing works. That is, if you twice do `module X; class Y; ...; end; end`,
148
+ it will both times open the same class X::Y.
data/examples/test.rake CHANGED
@@ -1,37 +1,65 @@
1
+ #--
2
+ # Copyright 2009 by Stefan Rusterholz.
3
+ # All rights reserved.
4
+ # See LICENSE.txt for permissions.
5
+ #++
6
+
7
+
8
+
1
9
  # This rake task expects to be in PROJECT_DIR/tasks/test.rake
2
10
  # It assumes that the tests are in PROJECT_DIR/test/**/*.rb
3
11
  # This is relevant as it calculates the paths accordingly.
4
- # Additionally it will add PROJECT_DIR/lib - if present - to $LOAD_PATH.
12
+ # It uses BareTest.load_standard_test_files to load setup and test files.
13
+ # This means it will also load a test/setup.rb file if present, where
14
+ # you can add paths to $LOAD_PATH.
5
15
 
6
- desc "Run testsuite. Set FORMAT env variable to change the formatter used."
7
- task :test do
8
- begin
9
- require 'test'
10
- rescue LoadError => e
11
- puts "Could not run tests: #{e}"
12
- else
13
- # Prepare paths
14
- rake_file = File.expand_path(__FILE__)
15
- test_dir = File.expand_path("#{rake_file}/../../test")
16
- lib_dir = File.expand_path("#{rake_file}/../../lib")
16
+ namespace :test do
17
+ desc "Information about how your test directory should look."
18
+ task :structure do
19
+ wd = File.expand_path(Dir.getwd)
20
+ rake_file = File.expand_path(__FILE__)
21
+ test_dir = ['./test', "#{rake_file}/../../test"].map { |path|
22
+ full = File.expand_path(path)
23
+ relative = full[(wd.size+1)..-1]
24
+ "* #{relative} (#{full})"
25
+ }
17
26
 
18
- # Verify that the test directory exists
19
- raise "Could not determine test directory, please adapt this rake task to " \
20
- "your directory structure first." unless File.directory?(test_dir)
27
+ puts "rake test:run expects to find one of the these directories:", *test_dir
28
+ end
21
29
 
22
- # Add PROJECT_DIR/lib to $LOAD_PATH if the dir exists
23
- if File.directory?(lib_dir) && !$LOAD_PATH.include?(lib_dir) then
24
- $LOAD_PATH.unshift(lib_dir)
25
- puts "Added '#{lib_dir}' to $LOAD_PATH" if $VERBOSE
26
- end
27
-
28
- # Load all test definitions
29
- Dir.glob(File.expand_path("#{test_dir}/**/*.rb")) { |path|
30
- require path
31
- }
32
-
33
- # Run all tests
34
- formatter = ENV["FORMAT"] || 'cli'
35
- Test.run.run(formatter)
36
- end
30
+ desc "Run testsuite. Set FORMAT env variable to change the formatter used, INTERACTIVE to have irb mode."
31
+ task :run do
32
+ begin
33
+ require 'baretest'
34
+ rescue LoadError => e
35
+ puts "Could not run tests: #{e}"
36
+ else
37
+ # Prepare paths
38
+ rake_file = File.expand_path(__FILE__)
39
+ test_dir = ["#{rake_file}/../../test", './test'].map { |path|
40
+ File.expand_path(path)
41
+ }.find { |path|
42
+ File.directory?(path)
43
+ }
44
+
45
+ # Verify that the test directory exists
46
+ raise "Could not determine test directory, please adapt this rake task to " \
47
+ "your directory structure first (see rake test:structure)." unless test_dir
48
+
49
+ # Load all test definitions
50
+ BareTest.load_standard_test_files(
51
+ :verbose => $VERBOSE,
52
+ :setup_file => 'test/setup.rb',
53
+ :chdir => File.dirname(test_dir) # must chdir to 1 above the 'test' dir
54
+ )
55
+
56
+ # Run all tests
57
+ format = ENV["FORMAT"] || 'cli'
58
+ interactive = ENV["INTERACTIVE"] == 'true'
59
+ BareTest.run(:format => format, :interactive => interactive)
60
+ end
61
+ end
37
62
  end
63
+
64
+ desc 'Alias for test:run'
65
+ task :test => 'test:run'
@@ -0,0 +1,26 @@
1
+ #--
2
+ # Copyright 2009 by Stefan Rusterholz.
3
+ # All rights reserved.
4
+ # See LICENSE.txt for permissions.
5
+ #++
6
+
7
+
8
+
9
+ BareTest.suite "Failure" do
10
+ setup do
11
+ @a = 1
12
+ @b = 2
13
+ end
14
+
15
+ assert "This one should fail and thus drop you into irb" do
16
+ c = 3
17
+ d = 4
18
+ @a == d
19
+ end
20
+
21
+ assert "This one should error and thus drop you into irb" do
22
+ c = 3
23
+ d = 4
24
+ raise "error!"
25
+ end
26
+ end
@@ -0,0 +1,57 @@
1
+ $LOAD_PATH.unshift(File.expand_path("#{__FILE__}/../../lib"))
2
+ require 'baretest'
3
+
4
+ BareTest.toplevel_suite.setup do
5
+ @_mymockname = {
6
+ :mocks => [],
7
+ :failures => [],
8
+ :exceptions => []
9
+ }
10
+ end
11
+ BareTest.toplevel_suite.teardown do
12
+ @_mymockname[:mocks].each { |mock|
13
+ mock.teardown(@_mymockname)
14
+ }
15
+ unless @_mymockname[:exceptions].empty? then
16
+ @reason = "An error occurred"
17
+ @exception = @_mymockname[:exceptions].first
18
+ @status = :error
19
+ end
20
+ unless @status == :error || @_mymockname[:failures].empty?
21
+ @reason = @_mymockname[:failures].first
22
+ @status = :failure
23
+ end
24
+ end
25
+
26
+ class DemoMock
27
+ class Error < StandardError; end
28
+
29
+ def initialize(action, message)
30
+ @action, @message = action, message
31
+ end
32
+
33
+ def teardown(recorder)
34
+ case @action
35
+ when :fail
36
+ recorder[:failures] << @message
37
+ when :raise
38
+ raise @message
39
+ end
40
+ rescue Error => e
41
+ recorder[:exceptions] << e
42
+ end
43
+ end
44
+
45
+ module MockSupport
46
+ def demo_mock(*args, &block)
47
+ mock = DemoMock.new(*args, &block)
48
+ @_mymockname[:mocks] << mock
49
+ mock
50
+ end
51
+ end
52
+
53
+ module BareTest
54
+ class Assertion
55
+ include MockSupport
56
+ end
57
+ end
@@ -0,0 +1,19 @@
1
+ BareTest.suite "MockDemo" do
2
+ suite "nothing happens" do
3
+ assert "Success" do
4
+ demo_mock(nil, nil)
5
+ end
6
+ end
7
+
8
+ suite "mock fails" do
9
+ assert "Failure" do
10
+ demo_mock(:fail, "this is the mock failure message")
11
+ end
12
+ end
13
+
14
+ suite "mock errors" do
15
+ assert "Exception" do
16
+ demo_mock(:raise, DemoMock::Error.new("mock errors message"))
17
+ end
18
+ end
19
+ end
@@ -0,0 +1,89 @@
1
+ BareTest.suite do
2
+ # assertions and refutations can be grouped in suites. They will share
3
+ # setup and teardown
4
+ # they don't have to be in suites, though
5
+ suite "Success" do
6
+ assert "An assertion returning a trueish value (non nil/false) is a success" do
7
+ true
8
+ end
9
+ end
10
+
11
+ suite "Failure" do
12
+ assert "An assertion returning a falsish value (nil/false) is a failure" do
13
+ false
14
+ end
15
+ end
16
+
17
+ suite "Pending" do
18
+ assert "An assertion without a block is pending"
19
+ end
20
+
21
+ suite "Error" do
22
+ assert "Uncaught exceptions in an assertion are an error" do
23
+ raise "Error!"
24
+ end
25
+ end
26
+
27
+ suite "Special assertions" do
28
+ assert "Assert a block to raise" do
29
+ raises do
30
+ sleep(rand()/3+0.05)
31
+ raise "If this raises then the assertion is a success"
32
+ end
33
+ end
34
+
35
+ assert "Assert a float to be close to another" do
36
+ a = 0.18 - 0.01
37
+ b = 0.17
38
+ within_delta a, b, 0.001
39
+ end
40
+
41
+ suite "Nested suite" do
42
+ assert "Assert two randomly ordered arrays to contain the same values" do
43
+ a = [*"A".."Z"] # an array with values from A to Z
44
+ b = a.sort_by { rand }
45
+ equal_unordered(a, b) # can be used with any Enumerable, uses hash-key identity
46
+ end
47
+ end
48
+ end
49
+
50
+ suite "Setup & Teardown" do
51
+ setup do
52
+ @foo = "foo"
53
+ @bar = "bar"
54
+ end
55
+
56
+ assert "@foo should be set" do
57
+ @foo == "foo"
58
+ end
59
+
60
+ suite "Nested suite" do
61
+ setup do
62
+ @bar = "inner bar"
63
+ @baz = "baz"
64
+ end
65
+
66
+ assert "@foo is inherited" do
67
+ @foo == "foo"
68
+ end
69
+
70
+ assert "@bar is overridden" do
71
+ @bar == "inner bar"
72
+ end
73
+
74
+ assert "@baz is defined only for inner" do
75
+ @baz == "baz"
76
+ end
77
+ end
78
+
79
+ teardown do
80
+ @foo = nil # not that it'd make much sense, just to demonstrate
81
+ end
82
+ end
83
+
84
+ suite "Dependencies", :requires => ['foo', 'bar'] do
85
+ assert "Will be skipped, due to unsatisfied dependencies" do
86
+ failure "Why the heck do you have a 'foo/bar' file?"
87
+ end
88
+ end
89
+ end