From 04f2b8f7bf16ad37d3c28f0e06eb02d63ab6a731 Mon Sep 17 00:00:00 2001 From: ntalbott Date: Wed, 12 Feb 2003 03:12:14 +0000 Subject: Initial revision git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@3477 b2dd03c8-39d4-4d8f-98ff-823fe69b080e --- lib/test/unit/testcase.rb | 152 ++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 152 insertions(+) create mode 100644 lib/test/unit/testcase.rb (limited to 'lib/test/unit/testcase.rb') diff --git a/lib/test/unit/testcase.rb b/lib/test/unit/testcase.rb new file mode 100644 index 0000000000..2ccf192906 --- /dev/null +++ b/lib/test/unit/testcase.rb @@ -0,0 +1,152 @@ +# :nodoc: +# +# Author:: Nathaniel Talbott. +# Copyright:: Copyright (c) 2000-2002 Nathaniel Talbott. All rights reserved. +# License:: Ruby license. + +require 'test/unit/assertions' +require 'test/unit/failure' +require 'test/unit/error' +require 'test/unit/testsuite' +require 'test/unit/assertionfailederror' + +module Test + module Unit + + # Ties everything together. If you subclass and add your own + # test methods, it takes care of making them into tests and + # wrapping those tests into a suite. It also does the + # nitty-gritty of actually running an individual test and + # collecting its results into a Test::Unit::TestResult object. + class TestCase + include Assertions + + attr_reader :method_name + + STARTED = name + "::STARTED" + FINISHED = name + "::FINISHED" + + # Creates a new instance of the fixture for running the + # test represented by test_method_name. + def initialize(test_method_name) + if ((!respond_to?(test_method_name)) || (method(test_method_name).arity != 0)) + throw :invalid_test + end + @method_name = test_method_name + @test_passed = true + end + + # Rolls up all of the test* methods in the fixture into + # one suite, creating a new instance of the fixture for + # each method. + def self.suite + method_names = public_instance_methods(true) + tests = method_names.delete_if { |method_name| method_name !~ /^test.+/ } + suite = TestSuite.new(name) + tests.each do + |test| + catch(:invalid_test) do + suite << new(test) + end + end + if (suite.empty?) + catch(:invalid_test) do + suite << new(:default_test) + end + end + return suite + end + + # Runs the individual test method represented by this + # instance of the fixture, collecting statistics, failures + # and errors in result. + def run(result) + yield(STARTED, name) + @_result = result + begin + setup + send(@method_name) + rescue AssertionFailedError => e + add_failure(e.message, e.backtrace) + rescue StandardError, ScriptError + add_error($!) + ensure + begin + teardown + rescue AssertionFailedError => e + add_failure(e.message, e.backtrace) + rescue StandardError, ScriptError + add_error($!) + end + end + result.add_run + yield(FINISHED, name) + end + + # Called before every test method runs. Can be used + # to set up fixture information. + def setup + end + + # Called after every test method runs. Can be used to tear + # down fixture information. + def teardown + end + + def default_test + flunk("No tests were specified") + end + + # Returns whether this individual test passed or + # not. Primarily for use in teardown so that artifacts + # can be left behind if the test fails. + def passed? + return @test_passed + end + private :passed? + + def size # :nodoc: + 1 + end + + def add_assertion # :nodoc: + @_result.add_assertion + end + private :add_assertion + + def add_failure(message, all_locations=caller()) # :nodoc: + @test_passed = false + assertions_pattern = /[^A-Za-z_]assertions\.rb:/ + if (all_locations.detect { |entry| entry =~ assertions_pattern }) + all_locations.shift + until (all_locations[0] =~ assertions_pattern || all_locations.empty?) + all_locations.shift + end + location = all_locations.detect { |entry| entry !~ assertions_pattern } + else + location = all_locations[0] + end + location = location[/^.+:\d+/] + @_result.add_failure(Failure.new("#{name} [#{location}]", message)) + end + private :add_failure + + def add_error(exception) # :nodoc: + @test_passed = false + @_result.add_error(Error.new(name, exception)) + end + private :add_error + + # Returns a human-readable name for the specific test that + # this instance of TestCase represents. + def name + "#{@method_name}(#{self.class.name})" + end + + # Overriden to return #name. + def to_s + name + end + end + end +end -- cgit v1.2.3