Module BareTest::Assertion::Support
In: lib/baretest/assertion/support.rb

BareTest::Assertion::Support is per default included into BareTest::Assertion. It provides several methods to make it easier to write assertions.

Methods

Public Instance methods

Uses === to test whether the objects are equal

Can be used in either of the following ways:

  equal expected, actual
  equal :expected => expected, :actual => actual

[Source]

     # File lib/baretest/assertion/support.rb, line 263
263:       def case_equal(*args)
264:         expected, actual, message = extract_args(args, :expected, :actual, :message)
265: 
266:         unless expected === actual then
267:           failure_with_optional_message \
268:             "Expected %s to be case equal (===) to %p but was %p",
269:             "Expected %p but got %p",
270:             message, expected, actual
271:         end
272:         true
273: 
274:       rescue ::BareTest::Assertion::Failure, *::BareTest::Assertion::PassthroughExceptions
275:         ::Kernel.raise
276:       rescue Exception => e
277:         failure "Could not compare %p with %p due to %s", expected, actual, e
278:       end
equal(*args)

Alias for order_equal

To compare two collections (which must implement each) without considering order. E.g. two sets, or the keys of two hashes.

[Source]

     # File lib/baretest/assertion/support.rb, line 283
283:       def equal_unordered(*args)
284:         expected, actual, message = extract_args(args, :expected, :actual, :message)
285: 
286:         count = Hash.new(0)
287:         expected.each { |element| count[element] += 1 }
288:         actual.each   { |element| count[element] -= 1 }
289: 
290:         unless count.all? { |key, value| value.zero? } then
291:           only_in_expected = count.select { |ele, n| n > 0 }.map { |ele, n| ele }
292:           only_in_actual   = count.select { |ele, n| n < 0 }.map { |ele, n| ele }
293:           if message then
294:             failure "Expected %s to have the same items the same number of times, " \
295:                     "but %p are only in expected, and %p only in actual",
296:                     message, only_in_expected, only_in_actual
297:           else
298:             failure "Expected %p and %p to have the same items the same number of times, " \
299:                     "but %p are only in expected, and %p only in actual",
300:                     expected, actual, only_in_expected, only_in_actual
301:           end
302:         end
303:         true
304: 
305:       rescue ::BareTest::Assertion::Failure, *::BareTest::Assertion::PassthroughExceptions
306:         ::Kernel.raise
307:       rescue Exception => e
308:         failure "Could not compare %p with %p due to %s", expected, actual, e
309:       end

extract arg allows to use named or positional args

Example:

  extract_args([1,2,3], :foo, :bar, :baz) # => [1,2,3]
  extract_args({:foo => 1,:bar => 2, :baz => 3}, :foo, :bar, :baz) # => [1,2,3]

Usage:

  def foo(*args)
    x,y,z = extract_args(args, :x, :y, :z)
  end
  foo(1,2,3)
  foo(:x => 1, :y => 2, :z => 3) # equivalent to the one above

[Source]

     # File lib/baretest/assertion/support.rb, line 400
400:       def extract_args(args, *named)
401:         if args.size == 1 && Hash === args.first then
402:           args.first.values_at(*named)
403:         else
404:           args.first(named.size)
405:         end
406:       end

Raises Test::Assertion::Failure, which causes the Assertion to get the status :failure. Runs sprintf over message with *args Particularly useful with %p and %s.

[Source]

     # File lib/baretest/assertion/support.rb, line 376
376:       def failure(message="Assertion failed", *args)
377:         raise ::BareTest::Assertion::Failure, sprintf(message, *args)
378:       end

A method to make raising failures that only optionally have a message easier.

[Source]

     # File lib/baretest/assertion/support.rb, line 365
365:       def failure_with_optional_message(with_message, without_message, message, *args)
366:         if message then
367:           failure(with_message, message, *args)
368:         else
369:           failure(without_message, *args)
370:         end
371:       end

Uses eql? to test whether the objects are equal

Can be used in either of the following ways:

  equal expected, actual
  equal :expected => expected, :actual => actual

[Source]

     # File lib/baretest/assertion/support.rb, line 216
216:       def hash_key_equal(*args)
217:         expected, actual, message = extract_args(args, :expected, :actual, :message)
218: 
219:         unless expected.eql?(actual) then
220:           if message then
221:             failure "Expected %s to be hash-key equal (eql?) to %p but was %p", message, expected, actual
222:           else
223:             failure "Expected %p but got %p", expected, actual
224:           end
225:         end
226:         true
227: 
228:       rescue ::BareTest::Assertion::Failure, *::BareTest::Assertion::PassthroughExceptions
229:         ::Kernel.raise
230:       rescue Exception => e
231:         failure "Could not compare %p with %p due to %s", expected, actual, e
232:       end

Raises a Failure if the given object is not an instance of the given class

[Source]

     # File lib/baretest/assertion/support.rb, line 330
330:       def instance_of(*args)
331:         expected, actual, message = extract_args(args, :expected, :actual, :message)
332:         unless actual.instance_of?(expected) then
333:           failure_with_optional_message \
334:             "Expected %1$s to be an instance of %3$p, but was a %4$p",
335:             "Expected %2$p to be an instance of %1$p, but was a %3$p",
336:             message, expected, actual, actual.class
337:         end
338:         true
339: 
340:       rescue ::BareTest::Assertion::Failure, *::BareTest::Assertion::PassthroughExceptions
341:         ::Kernel.raise
342:       rescue Exception => e
343:         failure "Could not test whether %p is an instance of %p due to %s", actual, expected, e
344:       end

Raises a Failure if the given object is not an instance of the given class or a descendant thereof

[Source]

     # File lib/baretest/assertion/support.rb, line 313
313:       def kind_of(*args)
314:         expected, actual, message = extract_args(args, :expected, :actual, :message)
315:         unless actual.kind_of?(expected) then
316:           failure_with_optional_message \
317:             "Expected %1$s to be a kind of %3$p, but was a %4$p",
318:             "Expected %2$p to be a kind of %1$p, but was a %3$p",
319:             message, expected, actual, actual.class
320:         end
321:         true
322: 
323:       rescue ::BareTest::Assertion::Failure, *::BareTest::Assertion::PassthroughExceptions
324:         ::Kernel.raise
325:       rescue Exception => e
326:         failure "Could not test whether %p is a kind of %p due to %s", actual, expected, e
327:       end

Used to verify that something was not touched.

See touch

[Source]

     # File lib/baretest/assertion/support.rb, line 184
184:       def not_touched(thing=nil)
185:         touched(thing, 0)
186:       end

Uses == to test whether the objects are equal

Can be used in either of the following ways:

  equal expected, actual
  equal :expected => expected, :actual => actual

[Source]

     # File lib/baretest/assertion/support.rb, line 239
239:       def order_equal(*args)
240:         expected, actual, message = extract_args(args, :expected, :actual, :message)
241: 
242:         unless expected == actual then
243:           if message then
244:             failure "Expected %s to be order equal (==) to %p but was %p", message, expected, actual
245:           else
246:             failure "Expected %p but got %p", expected, actual
247:           end
248:         end
249:         true
250: 
251:       rescue ::BareTest::Assertion::Failure, *::BareTest::Assertion::PassthroughExceptions
252:         ::Kernel.raise
253:       rescue Exception => e
254:         failure "Could not compare %p with %p due to %s", expected, actual, e
255:       end

Will raise a Failure if the given block doesn‘t raise or raises a different exception than the one provided You can optionally give an options :with_message, which is tested with === against the exception message.

Examples:

  raises do raise "will work" end # => true
  raises SomeException do raise SomeException end # => true
  raises :with_message => "bar" do raise "bar" end # => true
  raises SomeException, :with_message => "bar"; raise SomeException, "bar" end # => true
  raises :with_message => /\Aknown \w+\z/; raise "known unknown" end # => true

[Source]

     # File lib/baretest/assertion/support.rb, line 93
 93:       def raises(expected_exception_class=nil, with_message=nil, opts={})
 94:         exception_class = expected_exception_class || StandardError
 95:         yield
 96:       rescue exception_class => exception
 97:         if expected_exception_class && exception.class != expected_exception_class then
 98:           failure "Expected the code to raise #{expected_exception_class}, but it raised #{exception.class} instead"
 99:         elsif with_message && !(with_message === exception.message) then
100:           failure "Expected the code to raise with the message %p, but the message was %p",
101:                   with_message, exception.message
102:         else
103:           true
104:         end
105:       rescue ::BareTest::Assertion::Failure, *::BareTest::Assertion::PassthroughExceptions
106:         ::Kernel.raise
107:       rescue => exception
108:         failure "Expected the code to raise #{expected_exception_class}, but it raised #{exception.class} instead"
109:       else
110:         if expected_exception_class then
111:           failure "Expected the code to raise #{expected_exception_class}, but nothing was raised"
112:         else
113:           failure "Expected the code to raise, but nothing was raised"
114:         end
115:       end

Will raise a Failure if the given block raises.

[Source]

     # File lib/baretest/assertion/support.rb, line 118
118:       def raises_nothing
119:         yield
120:       rescue ::BareTest::Assertion::Failure, *::BareTest::Assertion::PassthroughExceptions
121:         ::Kernel.raise
122:       rescue Exception => exception
123:         failure "Expected the code to raise nothing, but it raised #{exception.class} (#{exception.message})"
124:       else
125:         true
126:       end

Raises a Failure if the given object does not respond to all of the given method names. The method names may be specified as String or Symbol.

[Source]

     # File lib/baretest/assertion/support.rb, line 348
348:       def respond_to(obj, *methods)
349:         not_responded_to = methods.reject { |method_name| obj.respond_to?(method_name) }
350:         unless not_responded_to.empty? then
351:           must_respond_to  = methods.map { |m| m.to_sym.inspect }.join(', ')
352:           not_responded_to = not_responded_to.map { |m| m.to_sym.inspect }.join(', ')
353:           failure "Expected %1$s to respond to all of %2$s, but it did not respond to %3$s",
354:              obj, must_respond_to, not_responded_to
355:         end
356:         true
357: 
358:       rescue ::BareTest::Assertion::Failure, *::BareTest::Assertion::PassthroughExceptions
359:         ::Kernel.raise
360:       rescue Exception => e
361:         failure "Could not test whether %p responds to %p due to %s", obj, methods, e
362:       end

Uses equal? to test whether the objects are the same

Can be used in either of the following ways:

  same expected, actual
  same :expected => expected, :actual => actual

[Source]

     # File lib/baretest/assertion/support.rb, line 193
193:       def same(*args)
194:         expected, actual, message = extract_args(args, :expected, :actual, :message)
195: 
196:         unless expected.equal?(actual) then
197:           if message then
198:             failure "Expected %s to be the same (equal?) as %p but was %p", message, expected, actual
199:           else
200:             failure "Expected %p but got %p", expected, actual
201:           end
202:         end
203:         true
204: 
205:       rescue ::BareTest::Assertion::Failure, *::BareTest::Assertion::PassthroughExceptions
206:         ::Kernel.raise
207:       rescue Exception => e
208:         failure "Could not compare %p with %p due to %s", expected, actual, e
209:       end

Raises Test::Assertion::Skip, which causes the Assertion to get the status :skipped. Runs sprintf over message with *args Particularly useful with %p and %s.

[Source]

     # File lib/baretest/assertion/support.rb, line 383
383:       def skip(message="Assertion was skipped", *args)
384:         raise ::BareTest::Assertion::Skip, sprintf(message, *args)
385:       end

Use this method to test whether certain code (e.g. a callback) was reached. touch marks that it was reached, touched tests for whether it was reached.

Example:

  assert "Code in a Proc object is executed when invoking #call on it" do
    a_proc = proc { touch :executed }
    a_proc.call
    touched(:executed)
  end

[Source]

     # File lib/baretest/assertion/support.rb, line 153
153:       def touch(thing=nil)
154:         ::BareTest.touch(self, thing)
155:       end

Used to verify that something was touched. You can also verify that something was touched a specific amount of times.

See touch

[Source]

     # File lib/baretest/assertion/support.rb, line 161
161:       def touched(thing=nil, times=nil)
162:         touched_times = ::BareTest.touched(self, thing)
163:         if times then
164:           unless touched_times == times then
165:             if thing then
166:               failure "Expected the code to touch %p %s times, but did %s times", thing, times, touched_times
167:             else
168:               failure "Expected the code to touch %s times, but did %s times", times, touched_times
169:             end
170:           end
171:         elsif touched_times < 1 then
172:           if thing then
173:             failure "Expected the code to touch %p, but it was not touched", thing
174:           else
175:             failure "Expected the code to touch, but no touch happened"
176:           end
177:         end
178:         true
179:       end

For comparisons of Floats you shouldn‘t use == but for example a delta comparison instead, to take care of the possible rounding differences.

[Source]

     # File lib/baretest/assertion/support.rb, line 131
131:       def within_delta(a, b, delta)
132:         actual_delta = (a-b).abs
133:         if actual_delta >= delta then
134:           failure "Expected %p and %p to differ less than %p, but they were different by %p", a, b, delta, actual_delta
135:         else
136:           true
137:         end
138:       rescue ::BareTest::Assertion::Failure, *::BareTest::Assertion::PassthroughExceptions
139:         ::Kernel.raise
140:       rescue Exception => e
141:         failure "Could not compare %p with %p due to %s", a, b, e
142:       end

FIXME: undocumented and untested It‘s really ugly. You should use a mock instead.

[Source]

    # File lib/baretest/assertion/support.rb, line 48
48:       def yields(subject, meth, args, *expected)
49:         subject.__send__(meth, *args) do |*actual|
50:           current = expected.shift
51:           return false unless actual == current
52:         end
53:         return expected.empty?
54:       end

[Validate]