diff options
author | nobu <nobu@b2dd03c8-39d4-4d8f-98ff-823fe69b080e> | 2009-10-02 19:07:55 +0000 |
---|---|---|
committer | nobu <nobu@b2dd03c8-39d4-4d8f-98ff-823fe69b080e> | 2009-10-02 19:07:55 +0000 |
commit | 719b0f8e3037e1033726b6487d7b0d9fc1412e7d (patch) | |
tree | c5a08c8c9abae9b7f0514f680f56553a7a03656a /test/rake | |
parent | a0f667c33e24928374d494c9c33d0082355785e1 (diff) |
* lib/rake: updated to rake code to rake-0.8.7 source code base.
* lib/rake/loaders/makefile.rb (Rake::MakefileLoader#process_line):
respace dependencies too.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@25199 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
Diffstat (limited to 'test/rake')
51 files changed, 4240 insertions, 0 deletions
diff --git a/test/rake/capture_stdout.rb b/test/rake/capture_stdout.rb new file mode 100644 index 0000000000..f54ec42f69 --- /dev/null +++ b/test/rake/capture_stdout.rb @@ -0,0 +1,24 @@ +require 'stringio' + +# Mix-in for capturing standard output. +module CaptureStdout + def capture_stdout + s = StringIO.new + oldstdout = $stdout + $stdout = s + yield + s.string + ensure + $stdout = oldstdout + end + + def capture_stderr + s = StringIO.new + oldstderr = $stderr + $stderr = s + yield + s.string + ensure + $stderr = oldstderr + end +end diff --git a/test/rake/check_expansion.rb b/test/rake/check_expansion.rb new file mode 100644 index 0000000000..659cf71e51 --- /dev/null +++ b/test/rake/check_expansion.rb @@ -0,0 +1,5 @@ +if ARGV[0] != ARGV[1] + exit 1 +else + exit 0 +end diff --git a/test/rake/check_no_expansion.rb b/test/rake/check_no_expansion.rb new file mode 100644 index 0000000000..24f586a7f5 --- /dev/null +++ b/test/rake/check_no_expansion.rb @@ -0,0 +1,5 @@ +if ARGV[0] != ARGV[1] + exit 0 +else + exit 1 +end diff --git a/test/rake/data/chains/Rakefile b/test/rake/data/chains/Rakefile new file mode 100644 index 0000000000..31bdc2578d --- /dev/null +++ b/test/rake/data/chains/Rakefile @@ -0,0 +1,15 @@ +# -*- ruby -*- + +task :default => "play.app" + +file "play.scpt" => "base" do |t| + cp t.prerequisites.first, t.name +end + +rule ".app" => ".scpt" do |t| + cp t.source, t.name +end + +file 'base' do + touch 'base' +end diff --git a/test/rake/data/default/Rakefile b/test/rake/data/default/Rakefile new file mode 100644 index 0000000000..22ed5e0ca9 --- /dev/null +++ b/test/rake/data/default/Rakefile @@ -0,0 +1,19 @@ +#!/usr/bin/env ruby + +if ENV['TESTTOPSCOPE'] + puts "TOPSCOPE" +end + +task :default do + puts "DEFAULT" +end + +task :other => [:default] do + puts "OTHER" +end + +task :task_scope do + if ENV['TESTTASKSCOPE'] + puts "TASKSCOPE" + end +end diff --git a/test/rake/data/dryrun/Rakefile b/test/rake/data/dryrun/Rakefile new file mode 100644 index 0000000000..0a68a0d606 --- /dev/null +++ b/test/rake/data/dryrun/Rakefile @@ -0,0 +1,22 @@ +# + +task :default => ["temp_main"] + +file "temp_main" => [:all_apps] do touch "temp_main" end + +task :all_apps => [:one, :two] +task :one => ["temp_one"] +task :two => ["temp_two"] + +file "temp_one" do |t| + touch "temp_one" +end +file "temp_two" do |t| + touch "temp_two" +end + +task :clean do + ["temp_one", "temp_two", "temp_main"].each do |file| + rm_f file + end +end diff --git a/test/rake/data/file_creation_task/Rakefile b/test/rake/data/file_creation_task/Rakefile new file mode 100644 index 0000000000..94641b6972 --- /dev/null +++ b/test/rake/data/file_creation_task/Rakefile @@ -0,0 +1,33 @@ +#!/usr/bin/env ruby + +N = 2 + +task :default => :run + +BUILD_DIR = 'build' +task :clean do + rm_rf 'build' + rm_rf 'src' +end + +task :run + +TARGET_DIR = 'build/copies' + +FileList['src/*'].each do |src| + directory TARGET_DIR + target = File.join TARGET_DIR, File.basename(src) + file target => [src, TARGET_DIR] do + cp src, target + # sleep 3 if src !~ /foo#{N-1}$/ # I'm commenting out this sleep, it doesn't seem to do anything. + end + task :run => target +end + +task :prep => :clean do + mkdir_p 'src' + N.times do |n| + puts "DBG: Touching src/foo#{n}" + touch "src/foo#{n}" + end +end diff --git a/test/rake/data/imports/Rakefile b/test/rake/data/imports/Rakefile new file mode 100644 index 0000000000..6a60f612bc --- /dev/null +++ b/test/rake/data/imports/Rakefile @@ -0,0 +1,19 @@ +# -*- ruby -*- + +require 'rake/loaders/makefile' + +task :default + +task :other do + puts "OTHER" +end + +file "dynamic_deps" do |t| + open(t.name, "w") do |f| f.puts "puts 'DYNAMIC'" end +end + +import "dynamic_deps" +import "static_deps" +import "static_deps" +import "deps.mf" +puts "FIRST" diff --git a/test/rake/data/imports/deps.mf b/test/rake/data/imports/deps.mf new file mode 100644 index 0000000000..04643d0d8e --- /dev/null +++ b/test/rake/data/imports/deps.mf @@ -0,0 +1 @@ +default: other diff --git a/test/rake/data/multidesc/Rakefile b/test/rake/data/multidesc/Rakefile new file mode 100644 index 0000000000..5342481922 --- /dev/null +++ b/test/rake/data/multidesc/Rakefile @@ -0,0 +1,17 @@ +#!/usr/bin/env ruby + +task :b + +desc "A" +task :a + +desc "B" +task :b + +desc "A2" +task :a + +task :c + +desc "xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" +task :d diff --git a/test/rake/data/namespace/Rakefile b/test/rake/data/namespace/Rakefile new file mode 100644 index 0000000000..6de98edae9 --- /dev/null +++ b/test/rake/data/namespace/Rakefile @@ -0,0 +1,57 @@ +#!/usr/bin/env ruby + +desc "copy" +task :copy do + puts "COPY" +end + +namespace "nest" do + desc "nest copy" + task :copy do + puts "NEST COPY" + end + task :xx => :copy +end + +anon_ns = namespace do + desc "anonymous copy task" + task :copy do + puts "ANON COPY" + end +end + +desc "Top level task to run the anonymous version of copy" +task :anon => anon_ns[:copy] + +namespace "very" do + namespace "nested" do + task "run" => "rake:copy" + end +end + +namespace "a" do + desc "Run task in the 'a' namespace" + task "run" do + puts "IN A" + end +end + +namespace "b" do + desc "Run task in the 'b' namespace" + task "run" => "a:run" do + puts "IN B" + end +end + +namespace "file1" do + file "xyz.rb" do + puts "XYZ1" + end +end + +namespace "file2" do + file "xyz.rb" do + puts "XYZ2" + end +end + diff --git a/test/rake/data/rakelib/test1.rake b/test/rake/data/rakelib/test1.rake new file mode 100644 index 0000000000..bb1c419b40 --- /dev/null +++ b/test/rake/data/rakelib/test1.rake @@ -0,0 +1,3 @@ +task :default do + puts "TEST1" +end diff --git a/test/rake/data/rbext/rakefile.rb b/test/rake/data/rbext/rakefile.rb new file mode 100644 index 0000000000..670604d733 --- /dev/null +++ b/test/rake/data/rbext/rakefile.rb @@ -0,0 +1,3 @@ +task :default do + puts "OK" +end diff --git a/test/rake/data/sample.mf b/test/rake/data/sample.mf new file mode 100644 index 0000000000..778e9d456f --- /dev/null +++ b/test/rake/data/sample.mf @@ -0,0 +1,14 @@ +# Comments +a: a1 a2 a3 a4 +b: b1 b2 b3 \ + b4 b5 b6\ +# Mid: Comment +b7 + + a : a5 a6 a7 +c: c1 +d: d1 d2 \ + +e f : e1 f1 + +g\ 0: g1 g\ 2 g\ 3 g4 diff --git a/test/rake/data/statusreturn/Rakefile b/test/rake/data/statusreturn/Rakefile new file mode 100644 index 0000000000..68023052f8 --- /dev/null +++ b/test/rake/data/statusreturn/Rakefile @@ -0,0 +1,8 @@ +#!/usr/bin/env ruby + +task :exit5 do + exit(5) +end + +task :normal do +end diff --git a/test/rake/data/unittest/Rakefile b/test/rake/data/unittest/Rakefile new file mode 100644 index 0000000000..9c3b8ac11c --- /dev/null +++ b/test/rake/data/unittest/Rakefile @@ -0,0 +1 @@ +# Empty Rakefile for Unit Test diff --git a/test/rake/filecreation.rb b/test/rake/filecreation.rb new file mode 100644 index 0000000000..e4c6e347da --- /dev/null +++ b/test/rake/filecreation.rb @@ -0,0 +1,30 @@ +module FileCreation + OLDFILE = "testdata/old" + NEWFILE = "testdata/new" + + def create_timed_files(oldfile, *newfiles) + return if File.exist?(oldfile) && newfiles.all? { |newfile| File.exist?(newfile) } + old_time = create_file(oldfile) + newfiles.each do |newfile| + while create_file(newfile) <= old_time + sleep(0.1) + File.delete(newfile) rescue nil + end + end + end + + def create_dir(dirname) + FileUtils.mkdir_p(dirname) unless File.exist?(dirname) + File.stat(dirname).mtime + end + + def create_file(name) + create_dir(File.dirname(name)) + FileUtils.touch(name) unless File.exist?(name) + File.stat(name).mtime + end + + def delete_file(name) + File.delete(name) rescue nil + end +end diff --git a/test/rake/in_environment.rb b/test/rake/in_environment.rb new file mode 100644 index 0000000000..f0a340fac9 --- /dev/null +++ b/test/rake/in_environment.rb @@ -0,0 +1,30 @@ +module InEnvironment + private + + # Create an environment for a test. At the completion of the yielded + # block, the environment is restored to its original conditions. + def in_environment(settings) + original_settings = set_env(settings) + yield + ensure + set_env(original_settings) if original_settings + end + + # Set the environment according to the settings hash. + def set_env(settings) # :nodoc: + result = {} + settings.each do |k, v| + result[k] = ENV[k] + if k == 'PWD' + result[k] = Dir.pwd + Dir.chdir(v) + elsif v.nil? + ENV.delete(k) + else + ENV[k] = v + end + end + result + end + +end diff --git a/test/rake/rake_test_setup.rb b/test/rake/rake_test_setup.rb new file mode 100644 index 0000000000..de94d56b40 --- /dev/null +++ b/test/rake/rake_test_setup.rb @@ -0,0 +1,9 @@ +# Common setup for all test files. + +# require 'flexmock/test_unit' + +module TestMethods + def assert_exception(ex, msg=nil, &block) + assert_raise(ex, msg, &block) + end +end diff --git a/test/rake/reqfile.rb b/test/rake/reqfile.rb new file mode 100644 index 0000000000..5372544b66 --- /dev/null +++ b/test/rake/reqfile.rb @@ -0,0 +1,3 @@ +# For --require testing + +TESTING_REQUIRE << 1 diff --git a/test/rake/reqfile2.rb b/test/rake/reqfile2.rb new file mode 100644 index 0000000000..65993907ac --- /dev/null +++ b/test/rake/reqfile2.rb @@ -0,0 +1,3 @@ +# For --require testing + +TESTING_REQUIRE << 2 diff --git a/test/rake/reqfile3.rb b/test/rake/reqfile3.rb new file mode 100644 index 0000000000..11fc16b2ab --- /dev/null +++ b/test/rake/reqfile3.rb @@ -0,0 +1,3 @@ +# For --require testing + +TESTING_REQUIRE << 3 diff --git a/test/rake/shellcommand.rb b/test/rake/shellcommand.rb new file mode 100755 index 0000000000..58db8a0871 --- /dev/null +++ b/test/rake/shellcommand.rb @@ -0,0 +1,3 @@ +#!/usr/bin/env ruby + +exit((ARGV[0] || "0").to_i) diff --git a/test/rake/test_application.rb b/test/rake/test_application.rb new file mode 100755 index 0000000000..adaa0b1b20 --- /dev/null +++ b/test/rake/test_application.rb @@ -0,0 +1,687 @@ +require 'test/unit' +require 'rake' +require_relative 'capture_stdout' +require_relative 'in_environment' + +TESTING_REQUIRE = [ ] + +###################################################################### +class TestApplication < Test::Unit::TestCase + include CaptureStdout + include InEnvironment + BASEDIR = File.dirname(__FILE__) + + def defmock(*names, &block) + class << (@mock ||= Object.new); self; end.class_eval do + names.each do |name| + define_method(name, block) + end + end + @mock + end + + def setup + @app = Rake::Application.new + @app.options.rakelib = [] + end + + def test_constant_warning + err = capture_stderr do @app.instance_eval { const_warning("Task") } end + assert_match(/warning/i, err) + assert_match(/deprecated/i, err) + assert_match(/Task/i, err) + end + + def test_display_tasks + @app.options.show_task_pattern = // + @app.last_description = "COMMENT" + @app.define_task(Rake::Task, "t") + out = capture_stdout do @app.instance_eval { display_tasks_and_comments } end + assert_match(/^rake t/, out) + assert_match(/# COMMENT/, out) + end + + def test_display_tasks_with_long_comments + in_environment('RAKE_COLUMNS' => '80') do + @app.options.show_task_pattern = // + @app.last_description = "1234567890" * 8 + @app.define_task(Rake::Task, "t") + out = capture_stdout do @app.instance_eval { display_tasks_and_comments } end + assert_match(/^rake t/, out) + assert_match(/# 12345678901234567890123456789012345678901234567890123456789012345\.\.\./, out) + end + end + + def test_display_tasks_with_task_name_wider_than_tty_display + in_environment('RAKE_COLUMNS' => '80') do + @app.options.show_task_pattern = // + description = "something short" + task_name = "task name" * 80 + @app.last_description = "something short" + @app.define_task(Rake::Task, task_name ) + out = capture_stdout do @app.instance_eval { display_tasks_and_comments } end + # Ensure the entire task name is output and we end up showing no description + assert_match(/rake #{task_name} # .../, out) + end + end + + def test_display_tasks_with_very_long_task_name_to_a_non_tty_shows_name_and_comment + @app.options.show_task_pattern = // + @app.tty_output = false + description = "something short" + task_name = "task name" * 80 + @app.last_description = "something short" + @app.define_task(Rake::Task, task_name ) + out = capture_stdout do @app.instance_eval { display_tasks_and_comments } end + # Ensure the entire task name is output and we end up showing no description + assert_match(/rake #{task_name} # #{description}/, out) + end + + def test_display_tasks_with_long_comments_to_a_non_tty_shows_entire_comment + @app.options.show_task_pattern = // + @app.tty_output = false + @app.last_description = "1234567890" * 8 + @app.define_task(Rake::Task, "t") + out = capture_stdout do @app.instance_eval { display_tasks_and_comments } end + assert_match(/^rake t/, out) + assert_match(/# #{@app.last_description}/, out) + end + + def test_display_tasks_with_long_comments_to_a_non_tty_with_columns_set_truncates_comments + in_environment("RAKE_COLUMNS" => '80') do + @app.options.show_task_pattern = // + @app.tty_output = false + @app.last_description = "1234567890" * 8 + @app.define_task(Rake::Task, "t") + out = capture_stdout do @app.instance_eval { display_tasks_and_comments } end + assert_match(/^rake t/, out) + assert_match(/# 12345678901234567890123456789012345678901234567890123456789012345\.\.\./, out) + end + end + + def test_display_tasks_with_full_descriptions + @app.options.show_task_pattern = // + @app.options.full_description = true + @app.last_description = "COMMENT" + @app.define_task(Rake::Task, "t") + out = capture_stdout do @app.instance_eval { display_tasks_and_comments } end + assert_match(/^rake t$/, out) + assert_match(/^ {4}COMMENT$/, out) + end + + def test_finding_rakefile + in_environment("PWD" => File.join(BASEDIR, "data/unittest")) do + assert_match(/Rakefile/i, @app.instance_eval { have_rakefile }) + end + end + + def test_not_finding_rakefile + @app.instance_eval { @rakefiles = ['NEVER_FOUND'] } + assert( ! @app.instance_eval do have_rakefile end ) + assert_nil @app.rakefile + end + + def test_load_rakefile + in_environment("PWD" => File.join(BASEDIR, "data/unittest")) do + @app.instance_eval do + handle_options + options.silent = true + load_rakefile + end + assert_equal "rakefile", @app.rakefile.downcase + assert_match(%r(unittest$), Dir.pwd) + end + end + + def test_load_rakefile_from_subdir + in_environment("PWD" => File.join(BASEDIR, "data/unittest/subdir")) do + @app.instance_eval do + handle_options + options.silent = true + load_rakefile + end + assert_equal "rakefile", @app.rakefile.downcase + assert_match(%r(unittest$), Dir.pwd) + end + end + + def test_load_rakefile_not_found + in_environment("PWD" => "/", "RAKE_SYSTEM" => 'not_exist') do + @app.instance_eval do + handle_options + options.silent = true + end + ex = assert_raise(RuntimeError) do + @app.instance_eval do raw_load_rakefile end + end + assert_match(/no rakefile found/i, ex.message) + end + end + + def test_load_from_system_rakefile + system_dir = File.expand_path('../data/default', __FILE__) + in_environment('RAKE_SYSTEM' => system_dir) do + @app.options.rakelib = [] + @app.instance_eval do + handle_options + options.silent = true + options.load_system = true + options.rakelib = [] + load_rakefile + end + assert_equal system_dir, @app.system_dir + assert_nil @app.rakefile + end + end + + def test_windows + assert ! (@app.windows? && @app.unix?) + end + + def test_loading_imports + args = [] + mock = defmock(:load) {|*a| args << a} + @app.instance_eval do + add_loader("dummy", mock) + add_import("x.dummy") + load_imports + end + assert_equal([["x.dummy"]], args) + end + + def test_building_imported_files_on_demand + args = [] + callback = false + mock = defmock(:load) {|*a| args << a} + @app.instance_eval do + intern(Rake::Task, "x.dummy").enhance do callback = true end + add_loader("dummy", mock) + add_import("x.dummy") + load_imports + end + assert_equal([["x.dummy"]], args) + assert(callback) + end + + def test_handle_options_should_strip_options_from_ARGV + assert !@app.options.trace + + valid_option = '--trace' + ARGV.clear + ARGV << valid_option + + @app.handle_options + + assert !ARGV.include?(valid_option) + assert @app.options.trace + end + + def test_good_run + ran = false + ARGV.clear + ARGV << '--rakelib=""' + @app.options.silent = true + @app.instance_eval do + intern(Rake::Task, "default").enhance { ran = true } + end + in_environment("PWD" => File.join(BASEDIR, "data/default")) do + @app.run + end + assert ran + end + + def test_display_task_run + ran = false + ARGV.clear + ARGV << '-f' << '-s' << '--tasks' << '--rakelib=""' + @app.last_description = "COMMENT" + @app.define_task(Rake::Task, "default") + out = capture_stdout { @app.run } + assert @app.options.show_tasks + assert ! ran + assert_match(/rake default/, out) + assert_match(/# COMMENT/, out) + end + + def test_display_prereqs + ran = false + ARGV.clear + ARGV << '-f' << '-s' << '--prereqs' << '--rakelib=""' + @app.last_description = "COMMENT" + t = @app.define_task(Rake::Task, "default") + t.enhance([:a, :b]) + @app.define_task(Rake::Task, "a") + @app.define_task(Rake::Task, "b") + out = capture_stdout { @app.run } + assert @app.options.show_prereqs + assert ! ran + assert_match(/rake a$/, out) + assert_match(/rake b$/, out) + assert_match(/rake default\n( *(a|b)\n){2}/m, out) + end + + def test_bad_run + @app.intern(Rake::Task, "default").enhance { fail } + ARGV.clear + ARGV << '-f' << '-s' << '--rakelib=""' + assert_raise(SystemExit) { + err = capture_stderr { @app.run } + assert_match(/see full trace/, err) + } + ensure + ARGV.clear + end + + def test_bad_run_with_trace + @app.intern(Rake::Task, "default").enhance { fail } + ARGV.clear + ARGV << '-f' << '-s' << '-t' + assert_raise(SystemExit) { + err = capture_stderr { capture_stdout { @app.run } } + assert_no_match(/see full trace/, err) + } + ensure + ARGV.clear + end + + def test_run_with_bad_options + @app.intern(Rake::Task, "default").enhance { fail } + ARGV.clear + ARGV << '-f' << '-s' << '--xyzzy' + assert_raise(SystemExit) { + err = capture_stderr { capture_stdout { @app.run } } + } + ensure + ARGV.clear + end +end + + +###################################################################### +class TestApplicationOptions < Test::Unit::TestCase + include CaptureStdout + + def setup + clear_argv + RakeFileUtils.verbose_flag = false + RakeFileUtils.nowrite_flag = false + TESTING_REQUIRE.clear + end + + def teardown + clear_argv + RakeFileUtils.verbose_flag = false + RakeFileUtils.nowrite_flag = false + end + + def clear_argv + while ! ARGV.empty? + ARGV.pop + end + end + + def test_default_options + opts = command_line + assert_nil opts.classic_namespace + assert_nil opts.dryrun + assert_nil opts.full_description + assert_nil opts.ignore_system + assert_nil opts.load_system + assert_nil opts.nosearch + assert_equal ['rakelib'], opts.rakelib + assert_nil opts.show_prereqs + assert_nil opts.show_task_pattern + assert_nil opts.show_tasks + assert_nil opts.silent + assert_nil opts.trace + assert_equal ['rakelib'], opts.rakelib + assert ! RakeFileUtils.verbose_flag + assert ! RakeFileUtils.nowrite_flag + end + + def test_dry_run + flags('--dry-run', '-n') do |opts| + assert opts.dryrun + assert opts.trace + assert RakeFileUtils.verbose_flag + assert RakeFileUtils.nowrite_flag + end + end + + def test_describe + flags('--describe') do |opts| + assert opts.full_description + assert opts.show_tasks + assert_equal(//.to_s, opts.show_task_pattern.to_s) + end + end + + def test_describe_with_pattern + flags('--describe=X') do |opts| + assert opts.full_description + assert opts.show_tasks + assert_equal(/X/.to_s, opts.show_task_pattern.to_s) + end + end + + def test_execute + $xyzzy = 0 + flags('--execute=$xyzzy=1', '-e $xyzzy=1') do |opts| + assert_equal 1, $xyzzy + assert_equal :exit, @exit + $xyzzy = 0 + end + end + + def test_execute_and_continue + $xyzzy = 0 + flags('--execute-continue=$xyzzy=1', '-E $xyzzy=1') do |opts| + assert_equal 1, $xyzzy + assert_not_equal :exit, @exit + $xyzzy = 0 + end + end + + def test_execute_and_print + $xyzzy = 0 + flags('--execute-print=$xyzzy="pugh"', '-p $xyzzy="pugh"') do |opts| + assert_equal 'pugh', $xyzzy + assert_equal :exit, @exit + assert_match(/^pugh$/, @out) + $xyzzy = 0 + end + end + + def test_help + flags('--help', '-H', '-h') do |opts| + assert_match(/\Arake/, @out) + assert_match(/\boptions\b/, @out) + assert_match(/\btargets\b/, @out) + assert_equal :exit, @exit + assert_equal :exit, @exit + end + end + + def test_libdir + flags(['--libdir', 'xx'], ['-I', 'xx'], ['-Ixx']) do |opts| + $:.include?('xx') + end + ensure + $:.delete('xx') + end + + def test_rakefile + flags(['--rakefile', 'RF'], ['--rakefile=RF'], ['-f', 'RF'], ['-fRF']) do |opts| + assert_equal ['RF'], @app.instance_eval { @rakefiles } + end + end + + def test_rakelib + flags(['--rakelibdir', 'A:B:C'], ['--rakelibdir=A:B:C'], ['-R', 'A:B:C'], ['-RA:B:C']) do |opts| + assert_equal ['A', 'B', 'C'], opts.rakelib + end + end + + def test_require + flags(['--require', File.expand_path('../reqfile', __FILE__)], + "-r#{File.expand_path('../reqfile2', __FILE__)}", + "-r#{File.expand_path('../reqfile3', __FILE__)}") do |opts| + end + assert TESTING_REQUIRE.include?(1) + assert TESTING_REQUIRE.include?(2) + assert TESTING_REQUIRE.include?(3) + assert_equal 3, TESTING_REQUIRE.size + end + + def test_missing_require + ex = assert_raise(LoadError) do + flags(['--require', File.expand_path('../missing', __FILE__)]) do |opts| + end + end + assert_match(/no such file/, ex.message) + assert_match(/#{File.basename(File.dirname(__FILE__))}\/missing/, ex.message) + end + + def test_prereqs + flags('--prereqs', '-P') do |opts| + assert opts.show_prereqs + end + end + + def test_quiet + flags('--quiet', '-q') do |opts| + assert ! RakeFileUtils.verbose_flag + assert ! opts.silent + end + end + + def test_no_search + flags('--nosearch', '--no-search', '-N') do |opts| + assert opts.nosearch + end + end + + def test_silent + flags('--silent', '-s') do |opts| + assert ! RakeFileUtils.verbose_flag + assert opts.silent + end + end + + def test_system + flags('--system', '-g') do |opts| + assert opts.load_system + end + end + + def test_no_system + flags('--no-system', '-G') do |opts| + assert opts.ignore_system + end + end + + def test_trace + flags('--trace', '-t') do |opts| + assert opts.trace + assert RakeFileUtils.verbose_flag + assert ! RakeFileUtils.nowrite_flag + end + end + + def test_trace_rules + flags('--rules') do |opts| + assert opts.trace_rules + end + end + + def test_tasks + flags('--tasks', '-T') do |opts| + assert opts.show_tasks + assert_equal(//.to_s, opts.show_task_pattern.to_s) + end + flags(['--tasks', 'xyz'], ['-Txyz']) do |opts| + assert opts.show_tasks + assert_equal(/xyz/, opts.show_task_pattern) + end + end + + def test_verbose + flags('--verbose', '-V') do |opts| + assert RakeFileUtils.verbose_flag + assert ! opts.silent + end + end + + def test_version + flags('--version', '-V') do |opts| + assert_match(/\bversion\b/, @out) + assert_match(/\b#{RAKEVERSION}\b/, @out) + assert_equal :exit, @exit + end + end + + def test_classic_namespace + flags(['--classic-namespace'], ['-C', '-T', '-P', '-n', '-s', '-t']) do |opts| + assert opts.classic_namespace + assert_equal opts.show_tasks, $show_tasks + assert_equal opts.show_prereqs, $show_prereqs + assert_equal opts.trace, $trace + assert_equal opts.dryrun, $dryrun + assert_equal opts.silent, $silent + end + end + + def test_bad_option + capture_stderr do + ex = assert_raise(OptionParser::InvalidOption) do + flags('--bad-option') + end + if ex.message =~ /^While/ # Ruby 1.9 error message + assert_match(/while parsing/i, ex.message) + else # Ruby 1.8 error message + assert_match(/(invalid|unrecognized) option/i, ex.message) + assert_match(/--bad-option/, ex.message) + end + end + end + + def test_task_collection + command_line("a", "b") + assert_equal ["a", "b"], @tasks.sort + end + + def test_default_task_collection + command_line() + assert_equal ["default"], @tasks + end + + def test_environment_definition + ENV.delete('TESTKEY') + command_line("a", "TESTKEY=12") + assert_equal ["a"], @tasks.sort + assert '12', ENV['TESTKEY'] + end + + private + + def flags(*sets) + sets.each do |set| + ARGV.clear + @out = capture_stdout { + @exit = catch(:system_exit) { opts = command_line(*set) } + } + yield(@app.options) if block_given? + end + end + + def command_line(*options) + options.each do |opt| ARGV << opt end + @app = Rake::Application.new + def @app.exit(*args) + throw :system_exit, :exit + end + @app.instance_eval do + handle_options + collect_tasks + end + @tasks = @app.top_level_tasks + @app.options + end +end + +class TestTaskArgumentParsing < Test::Unit::TestCase + def setup + @app = Rake::Application.new + end + + def test_name_only + name, args = @app.parse_task_string("name") + assert_equal "name", name + assert_equal [], args + end + + def test_empty_args + name, args = @app.parse_task_string("name[]") + assert_equal "name", name + assert_equal [], args + end + + def test_one_argument + name, args = @app.parse_task_string("name[one]") + assert_equal "name", name + assert_equal ["one"], args + end + + def test_two_arguments + name, args = @app.parse_task_string("name[one,two]") + assert_equal "name", name + assert_equal ["one", "two"], args + end + + def test_can_handle_spaces_between_args + name, args = @app.parse_task_string("name[one, two,\tthree , \tfour]") + assert_equal "name", name + assert_equal ["one", "two", "three", "four"], args + end + + def test_keeps_embedded_spaces + name, args = @app.parse_task_string("name[a one ana, two]") + assert_equal "name", name + assert_equal ["a one ana", "two"], args + end + +end + +class TestTaskArgumentParsing < Test::Unit::TestCase + include InEnvironment + + def test_terminal_width_using_env + app = Rake::Application.new + in_environment('RAKE_COLUMNS' => '1234') do + assert_equal 1234, app.terminal_width + end + end + + def test_terminal_width_using_stty + app = Rake::Application.new + def app.unix?() true end + def app.dynamic_width_stty() 1235 end + def app.dynamic_width_tput() 0 end + in_environment('RAKE_COLUMNS' => nil) do + assert_equal 1235, app.terminal_width + end + end + + def test_terminal_width_using_tput + app = Rake::Application.new + def app.unix?() true end + def app.dynamic_width_stty() 0 end + def app.dynamic_width_tput() 1236 end + in_environment('RAKE_COLUMNS' => nil) do + assert_equal 1236, app.terminal_width + end + end + + def test_terminal_width_using_hardcoded_80 + app = Rake::Application.new + def app.unix?() false end + in_environment('RAKE_COLUMNS' => nil) do + assert_equal 80, app.terminal_width + end + end + + def test_terminal_width_with_failure + app = Rake::Application.new + called = false + class << app; self; end.class_eval do + define_method(:unix?) {|*a| + called = a + raise RuntimeError + } + end + in_environment('RAKE_COLUMNS' => nil) do + assert_equal 80, app.terminal_width + end + assert_equal([], called) + end +end diff --git a/test/rake/test_clean.rb b/test/rake/test_clean.rb new file mode 100644 index 0000000000..35d99caa5a --- /dev/null +++ b/test/rake/test_clean.rb @@ -0,0 +1,12 @@ +require 'test/unit' +require 'rake/clean' + +class TestClean < Test::Unit::TestCase + include Rake + def test_clean + assert Task['clean'], "Should define clean" + assert Task['clobber'], "Should define clobber" + assert Task['clobber'].prerequisites.include?("clean"), + "Clobber should require clean" + end +end diff --git a/test/rake/test_definitions.rb b/test/rake/test_definitions.rb new file mode 100644 index 0000000000..a56d09b8d7 --- /dev/null +++ b/test/rake/test_definitions.rb @@ -0,0 +1,81 @@ +require 'test/unit' +require 'fileutils' +require 'rake' +require_relative 'filecreation' + +###################################################################### +class TestDefinitions < Test::Unit::TestCase + include Rake + + EXISTINGFILE = "testdata/existing" + + def setup + Task.clear + end + + def test_task + done = false + task :one => [:two] do done = true end + task :two + task :three => [:one, :two] + check_tasks(:one, :two, :three) + assert done, "Should be done" + end + + def test_file_task + done = false + file "testdata/one" => "testdata/two" do done = true end + file "testdata/two" + file "testdata/three" => ["testdata/one", "testdata/two"] + check_tasks("testdata/one", "testdata/two", "testdata/three") + assert done, "Should be done" + end + + def check_tasks(n1, n2, n3) + t = Task[n1] + assert Task === t, "Should be a Task" + assert_equal n1.to_s, t.name + assert_equal [n2.to_s], t.prerequisites.collect{|n| n.to_s} + t.invoke + t2 = Task[n2] + assert_equal FileList[], t2.prerequisites + t3 = Task[n3] + assert_equal [n1.to_s, n2.to_s], t3.prerequisites.collect{|n|n.to_s} + end + + def test_incremental_definitions + runs = [] + task :t1 => [:t2] do runs << "A"; 4321 end + task :t1 => [:t3] do runs << "B"; 1234 end + task :t1 => [:t3] + task :t2 + task :t3 + Task[:t1].invoke + assert_equal ["A", "B"], runs + assert_equal ["t2", "t3"], Task[:t1].prerequisites + end + + def test_missing_dependencies + task :x => ["testdata/missing"] + assert_raise(RuntimeError) { Task[:x].invoke } + end + + def test_implicit_file_dependencies + runs = [] + create_existing_file + task :y => [EXISTINGFILE] do |t| runs << t.name end + Task[:y].invoke + assert_equal runs, ['y'] + end + + private # ---------------------------------------------------------- + + def create_existing_file + Dir.mkdir File.dirname(EXISTINGFILE) unless + File.exist?(File.dirname(EXISTINGFILE)) + open(EXISTINGFILE, "w") do |f| f.puts "HI" end unless + File.exist?(EXISTINGFILE) + end + +end + diff --git a/test/rake/test_earlytime.rb b/test/rake/test_earlytime.rb new file mode 100644 index 0000000000..d166c25721 --- /dev/null +++ b/test/rake/test_earlytime.rb @@ -0,0 +1,33 @@ +require 'test/unit' +require 'rake' + +class TestEarlyTime < Test::Unit::TestCase + def test_create + early = Rake::EarlyTime.instance + time = Time.mktime(1970, 1, 1, 0, 0, 0) + assert early <= Time.now + assert early < Time.now + assert early != Time.now + assert Time.now > early + assert Time.now >= early + assert Time.now != early + end + + def test_equality + early = Rake::EarlyTime.instance + assert_equal early, early, "two early times should be equal" + end + + def test_original_time_compare_is_not_messed_up + t1 = Time.mktime(1970, 1, 1, 0, 0, 0) + t2 = Time.now + assert t1 < t2 + assert t2 > t1 + assert t1 == t1 + assert t2 == t2 + end + + def test_to_s + assert_equal "<EARLY TIME>", Rake::EARLY.to_s + end +end diff --git a/test/rake/test_extension.rb b/test/rake/test_extension.rb new file mode 100644 index 0000000000..0873efbe35 --- /dev/null +++ b/test/rake/test_extension.rb @@ -0,0 +1,61 @@ +require 'test/unit' +require 'rake' +require 'stringio' + +###################################################################### +class TestExtension < Test::Unit::TestCase + + module Redirect + def error_redirect + old_err = $stderr + result = StringIO.new + $stderr = result + yield + result + ensure + $stderr = old_err + end + end + + class Sample + extend Redirect + + def duplicate_method + :original + end + + OK_ERRS = error_redirect do + rake_extension("a") do + def ok_method + end + end + end + + + DUP_ERRS = error_redirect do + rake_extension("duplicate_method") do + def duplicate_method + :override + end + end + end + end + + def test_methods_actually_exist + sample = Sample.new + sample.ok_method + sample.duplicate_method + end + + def test_no_warning_when_defining_ok_method + assert_equal "", Sample::OK_ERRS.string + end + + def test_extension_complains_when_a_method_that_is_present + assert_match(/warning:/i, Sample::DUP_ERRS.string) + assert_match(/already exists/i, Sample::DUP_ERRS.string) + assert_match(/duplicate_method/i, Sample::DUP_ERRS.string) + assert_equal :original, Sample.new.duplicate_method + end + +end diff --git a/test/rake/test_file_creation_task.rb b/test/rake/test_file_creation_task.rb new file mode 100644 index 0000000000..1e5b177546 --- /dev/null +++ b/test/rake/test_file_creation_task.rb @@ -0,0 +1,60 @@ +require 'test/unit' +require 'fileutils' +require 'rake' +require_relative 'filecreation' + +###################################################################### +class TestFileCreationTask < Test::Unit::TestCase + include Rake + include FileCreation + + DUMMY_DIR = 'testdata/dummy_dir' + + def setup + Task.clear + end + + def teardown + FileUtils.rm_rf DUMMY_DIR + end + + def test_file_needed + create_dir DUMMY_DIR + fc_task = Task[DUMMY_DIR] + assert_equal DUMMY_DIR, fc_task.name + FileUtils.rm_rf fc_task.name + assert fc_task.needed?, "file should be needed" + FileUtils.mkdir fc_task.name + assert_equal nil, fc_task.prerequisites.collect{|n| Task[n].timestamp}.max + assert ! fc_task.needed?, "file should not be needed" + end + + def test_directory + directory DUMMY_DIR + fc_task = Task[DUMMY_DIR] + assert_equal DUMMY_DIR, fc_task.name + assert FileCreationTask === fc_task + end + + def test_no_retriggers_on_filecreate_task + create_timed_files(OLDFILE, NEWFILE) + t1 = Rake.application.intern(FileCreationTask, OLDFILE).enhance([NEWFILE]) + t2 = Rake.application.intern(FileCreationTask, NEWFILE) + assert ! t2.needed?, "Should not need to build new file" + assert ! t1.needed?, "Should not need to rebuild old file because of new" + end + + def test_no_retriggers_on_file_task + create_timed_files(OLDFILE, NEWFILE) + t1 = Rake.application.intern(FileCreationTask, OLDFILE).enhance([NEWFILE]) + t2 = Rake.application.intern(FileCreationTask, NEWFILE) + assert ! t2.needed?, "Should not need to build new file" + assert ! t1.needed?, "Should not need to rebuild old file because of new" + end + + def test_very_early_timestamp + t1 = Rake.application.intern(FileCreationTask, OLDFILE) + assert t1.timestamp < Time.now + assert t1.timestamp < Time.now - 1000000 + end +end diff --git a/test/rake/test_file_task.rb b/test/rake/test_file_task.rb new file mode 100644 index 0000000000..203597b789 --- /dev/null +++ b/test/rake/test_file_task.rb @@ -0,0 +1,139 @@ +require 'test/unit' +require 'fileutils' +require 'rake' +require_relative 'filecreation' + +###################################################################### +class TestFileTask < Test::Unit::TestCase + include Rake + include FileCreation + + def setup + Task.clear + @runs = Array.new + FileUtils.rm_f NEWFILE + FileUtils.rm_f OLDFILE + end + + def test_file_need + name = "testdata/dummy" + file name + ftask = Task[name] + assert_equal name.to_s, ftask.name + File.delete(ftask.name) rescue nil + assert ftask.needed?, "file should be needed" + open(ftask.name, "w") { |f| f.puts "HI" } + assert_equal nil, ftask.prerequisites.collect{|n| Task[n].timestamp}.max + assert ! ftask.needed?, "file should not be needed" + File.delete(ftask.name) rescue nil + end + + def test_file_times_new_depends_on_old + create_timed_files(OLDFILE, NEWFILE) + + t1 = Rake.application.intern(FileTask, NEWFILE).enhance([OLDFILE]) + t2 = Rake.application.intern(FileTask, OLDFILE) + assert ! t2.needed?, "Should not need to build old file" + assert ! t1.needed?, "Should not need to rebuild new file because of old" + end + + def test_file_times_old_depends_on_new + create_timed_files(OLDFILE, NEWFILE) + + t1 = Rake.application.intern(FileTask,OLDFILE).enhance([NEWFILE]) + t2 = Rake.application.intern(FileTask, NEWFILE) + assert ! t2.needed?, "Should not need to build new file" + preq_stamp = t1.prerequisites.collect{|t| Task[t].timestamp}.max + assert_equal t2.timestamp, preq_stamp + assert t1.timestamp < preq_stamp, "T1 should be older" + assert t1.needed?, "Should need to rebuild old file because of new" + end + + def test_file_depends_on_task_depend_on_file + create_timed_files(OLDFILE, NEWFILE) + + file NEWFILE => [:obj] do |t| @runs << t.name end + task :obj => [OLDFILE] do |t| @runs << t.name end + file OLDFILE do |t| @runs << t.name end + + Task[:obj].invoke + Task[NEWFILE].invoke + assert ! @runs.include?(NEWFILE) + end + + def test_existing_file_depends_on_non_existing_file + create_file(OLDFILE) + delete_file(NEWFILE) + file NEWFILE + file OLDFILE => NEWFILE + assert_nothing_raised do Task[OLDFILE].invoke end + end + + # I have currently disabled this test. I'm not convinced that + # deleting the file target on failure is always the proper thing to + # do. I'm willing to hear input on this topic. + def ztest_file_deletes_on_failure + task :obj + file NEWFILE => [:obj] do |t| + FileUtils.touch NEWFILE + fail "Ooops" + end + assert Task[NEWFILE] + begin + Task[NEWFILE].invoke + rescue Exception + end + assert( ! File.exist?(NEWFILE), "NEWFILE should be deleted") + end + +end + +###################################################################### +class TestDirectoryTask < Test::Unit::TestCase + include Rake + + def setup + rm_rf "testdata", :verbose=>false + end + + def teardown + rm_rf "testdata", :verbose=>false + end + + def test_directory + desc "DESC" + directory "testdata/a/b/c" + assert_equal FileCreationTask, Task["testdata"].class + assert_equal FileCreationTask, Task["testdata/a"].class + assert_equal FileCreationTask, Task["testdata/a/b/c"].class + assert_nil Task["testdata"].comment + assert_equal "DESC", Task["testdata/a/b/c"].comment + assert_nil Task["testdata/a/b"].comment + verbose(false) { + Task['testdata/a/b'].invoke + } + assert File.exist?("testdata/a/b") + assert ! File.exist?("testdata/a/b/c") + end + + if Rake::Win32.windows? + def test_directory_win32 + desc "WIN32 DESC" + FileUtils.mkdir_p("testdata") + Dir.chdir("testdata") do + directory 'c:/testdata/a/b/c' + assert_equal FileCreationTask, Task['c:/testdata'].class + assert_equal FileCreationTask, Task['c:/testdata/a'].class + assert_equal FileCreationTask, Task['c:/testdata/a/b/c'].class + assert_nil Task['c:/testdata'].comment + assert_equal "WIN32 DESC", Task['c:/testdata/a/b/c'].comment + assert_nil Task['c:/testdata/a/b'].comment + verbose(false) { + Task['c:/testdata/a/b'].invoke + } + assert File.exist?('c:/testdata/a/b') + assert ! File.exist?('c:/testdata/a/b/c') + end + end + end +end diff --git a/test/rake/test_filelist.rb b/test/rake/test_filelist.rb new file mode 100644 index 0000000000..da7b37bd4b --- /dev/null +++ b/test/rake/test_filelist.rb @@ -0,0 +1,625 @@ +require 'test/unit' +require 'tmpdir' +require 'rake' + +require_relative 'capture_stdout' + +class TestFileList < Test::Unit::TestCase + FileList = Rake::FileList + include CaptureStdout + + def setup + @oldwd = Dir.pwd + @tmpwd = Dir.mktmpdir + Dir.chdir(@tmpwd) + create_test_data + end + + def teardown +# FileList.select_default_ignore_patterns + FileUtils.rm_rf("testdata") + Dir.chdir(@oldwd) + FileUtils.rm_rf(@tmpwd) + end + + def test_delgating_methods_do_not_include_to_a_or_to_ary + assert ! FileList::DELEGATING_METHODS.include?("to_a"), "should not include to_a" + assert ! FileList::DELEGATING_METHODS.include?(:to_a), "should not include to_a" + assert ! FileList::DELEGATING_METHODS.include?("to_ary"), "should not include to_ary" + assert ! FileList::DELEGATING_METHODS.include?(:to_ary), "should not include to_ary" + end + + def test_create + fl = FileList.new + assert_equal 0, fl.size + end + + def test_create_with_args + fl = FileList.new("testdata/*.c", "x") + assert_equal ["testdata/abc.c", "testdata/x.c", "testdata/xyz.c", "x"].sort, + fl.sort + end + + def test_create_with_block + fl = FileList.new { |f| f.include("x") } + assert_equal ["x"], fl.resolve + end + + def test_create_with_brackets + fl = FileList["testdata/*.c", "x"] + assert_equal ["testdata/abc.c", "testdata/x.c", "testdata/xyz.c", "x"].sort, + fl.sort + end + + def test_create_with_brackets_and_filelist + fl = FileList[FileList["testdata/*.c", "x"]] + assert_equal ["testdata/abc.c", "testdata/x.c", "testdata/xyz.c", "x"].sort, + fl.sort + end + + def test_include_with_another_array + fl = FileList.new.include(["x", "y", "z"]) + assert_equal ["x", "y", "z"].sort, fl.sort + end + + def test_include_with_another_filelist + fl = FileList.new.include(FileList["testdata/*.c", "x"]) + assert_equal ["testdata/abc.c", "testdata/x.c", "testdata/xyz.c", "x"].sort, + fl.sort + end + + def test_append + fl = FileList.new + fl << "a.rb" << "b.rb" + assert_equal ['a.rb', 'b.rb'], fl + end + + def test_add_many + fl = FileList.new + fl.include %w(a d c) + fl.include('x', 'y') + assert_equal ['a', 'd', 'c', 'x', 'y'], fl + assert_equal ['a', 'd', 'c', 'x', 'y'], fl.resolve + end + + def test_add_return + f = FileList.new + g = f << "x" + assert_equal f.object_id, g.object_id + h = f.include("y") + assert_equal f.object_id, h.object_id + end + + def test_match + fl = FileList.new + fl.include(File.expand_path('../test*.rb', __FILE__)) + assert fl.include?(__FILE__) + assert fl.size > 3 + fl.each { |fn| assert_match(/\.rb$/, fn) } + end + + def test_add_matching + fl = FileList.new + fl << "a.java" + fl.include(File.dirname(__FILE__)+"/*.rb") + assert_equal "a.java", fl[0] + assert fl.size > 2 + assert fl.include?(__FILE__) + end + + def test_multiple_patterns + create_test_data + fl = FileList.new + fl.include('*.c', '*xist*') + assert_equal [], fl + fl.include('testdata/*.c', 'testdata/*xist*') + assert_equal [ + 'testdata/x.c', 'testdata/xyz.c', 'testdata/abc.c', 'testdata/existing' + ].sort, fl.sort + end + + def test_square_bracket_pattern + fl = FileList.new + fl.include("testdata/abc.[ch]") + assert fl.size == 2 + assert fl.include?("testdata/abc.c") + assert fl.include?("testdata/abc.h") + end + + def test_curly_bracket_pattern + fl = FileList.new + fl.include("testdata/abc.{c,h}") + assert fl.size == 2 + assert fl.include?("testdata/abc.c") + assert fl.include?("testdata/abc.h") + end + + def test_reject + fl = FileList.new + fl.include %w(testdata/x.c testdata/abc.c testdata/xyz.c testdata/existing) + fl.reject! { |fn| fn =~ %r{/x} } + assert_equal [ + 'testdata/abc.c', 'testdata/existing' + ], fl + end + + def test_exclude + fl = FileList['testdata/x.c', 'testdata/abc.c', 'testdata/xyz.c', 'testdata/existing'] + fl.each { |fn| touch fn, :verbose => false } + x = fl.exclude(%r{/x.+\.}) + assert_equal FileList, x.class + assert_equal %w(testdata/x.c testdata/abc.c testdata/existing), fl + assert_equal fl.object_id, x.object_id + fl.exclude('testdata/*.c') + assert_equal ['testdata/existing'], fl + fl.exclude('testdata/existing') + assert_equal [], fl + end + + def test_excluding_via_block + fl = FileList['testdata/a.c', 'testdata/b.c', 'testdata/xyz.c'] + fl.exclude { |fn| fn.pathmap('%n') == 'xyz' } + assert fl.exclude?("xyz.c"), "Should exclude xyz.c" + assert_equal ['testdata/a.c', 'testdata/b.c'], fl + end + + def test_exclude_return_on_create + fl = FileList['testdata/*'].exclude(/.*\.[hcx]$/) + assert_equal ['testdata/existing', 'testdata/cfiles'].sort, fl.sort + assert_equal FileList, fl.class + end + + def test_exclude_with_string_return_on_create + fl = FileList['testdata/*'].exclude('testdata/abc.c') + assert_equal %w(testdata/existing testdata/cfiles testdata/x.c testdata/abc.h testdata/abc.x testdata/xyz.c).sort, fl.sort + assert_equal FileList, fl.class + end + + def test_default_exclude + fl = FileList.new + fl.clear_exclude + fl.include("**/*~", "**/*.bak", "**/core") + assert fl.member?("testdata/core"), "Should include core" + assert fl.member?("testdata/x.bak"), "Should include .bak files" + end + + def test_unique + fl = FileList.new + fl << "x.c" << "a.c" << "b.rb" << "a.c" + assert_equal ['x.c', 'a.c', 'b.rb', 'a.c'], fl + fl.uniq! + assert_equal ['x.c', 'a.c', 'b.rb'], fl + end + + def test_to_string + fl = FileList.new + fl << "a.java" << "b.java" + assert_equal "a.java b.java", fl.to_s + assert_equal "a.java b.java", "#{fl}" + end + + def test_to_array + fl = FileList['a.java', 'b.java'] + assert_equal ['a.java', 'b.java'], fl.to_a + assert_equal Array, fl.to_a.class + assert_equal ['a.java', 'b.java'], fl.to_ary + assert_equal Array, fl.to_ary.class + end + + def test_to_s_pending + fl = FileList['testdata/abc.*'] + result = fl.to_s + assert_match(%r{testdata/abc\.c}, result) + assert_match(%r{testdata/abc\.h}, result) + assert_match(%r{testdata/abc\.x}, result) + assert_match(%r{(testdata/abc\..\b ?){2}}, result) + end + + def test_inspect_pending + fl = FileList['testdata/abc.*'] + result = fl.inspect + assert_match(%r{"testdata/abc\.c"}, result) + assert_match(%r{"testdata/abc\.h"}, result) + assert_match(%r{"testdata/abc\.x"}, result) + assert_match(%r|^\[("testdata/abc\..", ){2}"testdata/abc\.."\]$|, result) + end + + def test_sub + fl = FileList["testdata/*.c"] + f2 = fl.sub(/\.c$/, ".o") + assert_equal FileList, f2.class + assert_equal ["testdata/abc.o", "testdata/x.o", "testdata/xyz.o"].sort, + f2.sort + f3 = fl.gsub(/\.c$/, ".o") + assert_equal FileList, f3.class + assert_equal ["testdata/abc.o", "testdata/x.o", "testdata/xyz.o"].sort, + f3.sort + end + + def test_claim_to_be_a_kind_of_array + fl = FileList['testdata/*.c'] + assert fl.is_a?(Array) + assert fl.kind_of?(Array) + end + + def test_claim_to_be_a_kind_of_filelist + fl = FileList['testdata/*.c'] + assert fl.is_a?(FileList) + assert fl.kind_of?(FileList) + end + + def test_claim_to_be_a_filelist_instance + fl = FileList['testdata/*.c'] + assert fl.instance_of?(FileList) + end + + def test_dont_claim_to_be_an_array_instance + fl = FileList['testdata/*.c'] + assert ! fl.instance_of?(Array) + end + + def test_sub! + f = "x/a.c" + fl = FileList[f, "x/b.c"] + res = fl.sub!(/\.c$/, ".o") + assert_equal ["x/a.o", "x/b.o"].sort, fl.sort + assert_equal "x/a.c", f + assert_equal fl.object_id, res.object_id + end + + def test_sub_with_block + fl = FileList["src/org/onestepback/a.java", "src/org/onestepback/b.java"] +# The block version doesn't work the way I want it to ... +# f2 = fl.sub(%r{^src/(.*)\.java$}) { |x| "classes/" + $1 + ".class" } + f2 = fl.sub(%r{^src/(.*)\.java$}, "classes/\\1.class") + assert_equal [ + "classes/org/onestepback/a.class", + "classes/org/onestepback/b.class" + ].sort, + f2.sort + end + + def test_string_ext + assert_equal "one.net", "one.two".ext("net") + assert_equal "one.net", "one.two".ext(".net") + assert_equal "one.net", "one".ext("net") + assert_equal "one.net", "one".ext(".net") + assert_equal "one.two.net", "one.two.c".ext(".net") + assert_equal "one/two.net", "one/two.c".ext(".net") + assert_equal "one.x/two.net", "one.x/two.c".ext(".net") + assert_equal "one.x/two.net", "one.x/two".ext(".net") + assert_equal ".onerc.net", ".onerc.dot".ext("net") + assert_equal ".onerc.net", ".onerc".ext("net") + assert_equal ".a/.onerc.net", ".a/.onerc".ext("net") + assert_equal "one", "one.two".ext('') + assert_equal "one", "one.two".ext + assert_equal ".one", ".one.two".ext + assert_equal ".one", ".one".ext + assert_equal ".", ".".ext("c") + assert_equal "..", "..".ext("c") + # These only need to work in windows + if Rake::Win32.windows? + assert_equal "one.x\\two.net", "one.x\\two.c".ext(".net") + assert_equal "one.x\\two.net", "one.x\\two".ext(".net") + end + end + + def test_filelist_ext + assert_equal FileList['one.c', '.one.c'], + FileList['one.net', '.one'].ext('c') + end + + def test_gsub + create_test_data + fl = FileList["testdata/*.c"] + f2 = fl.gsub(/a/, "A") + assert_equal ["testdAtA/Abc.c", "testdAtA/x.c", "testdAtA/xyz.c"].sort, + f2.sort + end + + def test_gsub! + create_test_data + f = FileList["testdata/*.c"] + f.gsub!(/a/, "A") + assert_equal ["testdAtA/Abc.c", "testdAtA/x.c", "testdAtA/xyz.c"].sort, + f.sort + end + + def test_egrep_with_output + files = FileList[File.expand_path('../test*.rb', __FILE__)] + the_line_number = __LINE__ + 1 + out = capture_stdout do files.egrep(/PUGH/) end + assert_match(/:#{the_line_number}:/, out) + end + + def test_egrep_with_block + files = FileList[File.expand_path('../test*.rb', __FILE__)] + found = false + the_line_number = __LINE__ + 1 + files.egrep(/XYZZY/) do |fn, ln, line | + assert_equal __FILE__, fn + assert_equal the_line_number, ln + assert_match(/files\.egrep/, line) + found = true + end + assert found, "should have found a matching line" + end + + def test_existing + fl = FileList['testdata/abc.c', 'testdata/notthere.c'] + assert_equal ["testdata/abc.c"], fl.existing + assert fl.existing.is_a?(FileList) + end + + def test_existing! + fl = FileList['testdata/abc.c', 'testdata/notthere.c'] + result = fl.existing! + assert_equal ["testdata/abc.c"], fl + assert_equal fl.object_id, result.object_id + end + + def test_ignore_special + f = FileList['testdata/*'] + assert ! f.include?("testdata/CVS"), "Should not contain CVS" + assert ! f.include?("testdata/.svn"), "Should not contain .svn" + assert ! f.include?("testdata/.dummy"), "Should not contain dot files" + assert ! f.include?("testdata/x.bak"), "Should not contain .bak files" + assert ! f.include?("testdata/x~"), "Should not contain ~ files" + assert ! f.include?("testdata/core"), "Should not contain core files" + end + + def test_clear_ignore_patterns + f = FileList['testdata/*', 'testdata/.svn'] + f.clear_exclude + assert f.include?("testdata/abc.c") + assert f.include?("testdata/xyz.c") + assert f.include?("testdata/CVS") + assert f.include?("testdata/.svn") + assert f.include?("testdata/x.bak") + assert f.include?("testdata/x~") + end + + def test_exclude_with_alternate_file_seps + fl = FileList.new + assert fl.exclude?("x/CVS/y") + assert fl.exclude?("x\\CVS\\y") + assert fl.exclude?("x/.svn/y") + assert fl.exclude?("x\\.svn\\y") + assert fl.exclude?("x/core") + assert fl.exclude?("x\\core") + end + + def test_add_default_exclude_list + fl = FileList.new + fl.exclude(/~\d+$/) + assert fl.exclude?("x/CVS/y") + assert fl.exclude?("x\\CVS\\y") + assert fl.exclude?("x/.svn/y") + assert fl.exclude?("x\\.svn\\y") + assert fl.exclude?("x/core") + assert fl.exclude?("x\\core") + assert fl.exclude?("x/abc~1") + end + + def test_basic_array_functions + f = FileList['b', 'c', 'a'] + assert_equal 'b', f.first + assert_equal 'b', f[0] + assert_equal 'a', f.last + assert_equal 'a', f[2] + assert_equal 'a', f[-1] + assert_equal ['a', 'b', 'c'], f.sort + f.sort! + assert_equal ['a', 'b', 'c'], f + end + + def test_flatten + assert_equal ['a', 'testdata/x.c', 'testdata/xyz.c', 'testdata/abc.c'].sort, + ['a', FileList['testdata/*.c']].flatten.sort + end + + def test_clone_and_dup + a = FileList['a', 'b', 'c'] + c = a.clone + d = a.dup + a << 'd' + assert_equal ['a', 'b', 'c', 'd'], a + assert_equal ['a', 'b', 'c'], c + assert_equal ['a', 'b', 'c'], d + end + + def test_dup_and_clone_replicate_taint + a = FileList['a', 'b', 'c'] + a.taint + c = a.clone + d = a.dup + assert c.tainted?, "Clone should be tainted" + assert d.tainted?, "Dup should be tainted" + end + + def test_duped_items_will_thaw + a = FileList['a', 'b', 'c'] + a.freeze + d = a.dup + d << 'more' + assert_equal ['a', 'b', 'c', 'more'], d + end + + def test_cloned_items_stay_frozen + a = FileList['a', 'b', 'c'] + a.freeze + c = a.clone + assert_raise(TypeError, RuntimeError) do + c << 'more' + end + end + + def test_array_comparisons + fl = FileList['b', 'b'] + a = ['b', 'a'] + b = ['b', 'b'] + c = ['b', 'c'] + assert_equal( 1, fl <=> a ) + assert_equal( 0, fl <=> b ) + assert_equal( -1, fl <=> c ) + assert_equal( -1, a <=> fl ) + assert_equal( 0, b <=> fl ) + assert_equal( 1, c <=> fl ) + end + + def test_array_equality + a = FileList['a', 'b'] + b = ['a', 'b'] + assert a == b + assert b == a +# assert a.eql?(b) +# assert b.eql?(a) + assert ! a.equal?(b) + assert ! b.equal?(a) + end + + def test_enumeration_methods + a = FileList['a', 'b'] + b = a.collect { |it| it.upcase } + assert_equal ['A', 'B'], b + assert_equal FileList, b.class + + b = a.map { |it| it.upcase } + assert_equal ['A', 'B'], b + assert_equal FileList, b.class + + b = a.sort + assert_equal ['a', 'b'], b + assert_equal FileList, b.class + + b = a.sort_by { |it| it } + assert_equal ['a', 'b'], b + assert_equal FileList, b.class + + b = a.find_all { |it| it == 'b'} + assert_equal ['b'], b + assert_equal FileList, b.class + + b = a.select { |it| it.size == 1 } + assert_equal ['a', 'b'], b + assert_equal FileList, b.class + + b = a.reject { |it| it == 'b' } + assert_equal ['a'], b + assert_equal FileList, b.class + + b = a.grep(/./) + assert_equal ['a', 'b'], b + assert_equal FileList, b.class + + b = a.partition { |it| it == 'b' } + assert_equal [['b'], ['a']], b + assert_equal Array, b.class + assert_equal FileList, b[0].class + assert_equal FileList, b[1].class + + b = a.zip(['x', 'y']).to_a + assert_equal [['a', 'x'], ['b', 'y']], b + assert_equal Array, b.class + assert_equal Array, b[0].class + assert_equal Array, b[1].class + end + + def test_array_operators + a = ['a', 'b'] + b = ['c', 'd'] + f = FileList['x', 'y'] + g = FileList['w', 'z'] + + r = f + g + assert_equal ['x', 'y', 'w', 'z'], r + assert_equal FileList, r.class + + r = a + g + assert_equal ['a', 'b', 'w', 'z'], r + assert_equal Array, r.class + + r = f + b + assert_equal ['x', 'y', 'c', 'd'], r + assert_equal FileList, r.class + + r = FileList['w', 'x', 'y', 'z'] - f + assert_equal ['w', 'z'], r + assert_equal FileList, r.class + + r = FileList['w', 'x', 'y', 'z'] & f + assert_equal ['x', 'y'], r + assert_equal FileList, r.class + + r = f * 2 + assert_equal ['x', 'y', 'x', 'y'], r + assert_equal FileList, r.class + + r = f * ',' + assert_equal 'x,y', r + assert_equal String, r.class + + r = f | ['a', 'x'] + assert_equal ['a', 'x', 'y'].sort, r.sort + assert_equal FileList, r.class + end + + def test_other_array_returning_methods + f = FileList['a', nil, 'b'] + r = f.compact + assert_equal ['a', 'b'], r + assert_equal FileList, r.class + + f = FileList['a', 'b'] + r = f.concat(['x', 'y']) + assert_equal ['a', 'b', 'x', 'y'], r + assert_equal FileList, r.class + + f = FileList['a', ['b', 'c'], FileList['d', 'e']] + r = f.flatten + assert_equal ['a', 'b', 'c', 'd', 'e'], r + assert_equal FileList, r.class + + f = FileList['a', 'b', 'a'] + r = f.uniq + assert_equal ['a', 'b'], r + assert_equal FileList, r.class + + f = FileList['a', 'b', 'c', 'd'] + r = f.values_at(1,3) + assert_equal ['b', 'd'], r + assert_equal FileList, r.class + end + + def test_file_utils_can_use_filelists + cfiles = FileList['testdata/*.c'] + + cp cfiles, @cdir, :verbose => false + + assert File.exist?(File.join(@cdir, 'abc.c')) + assert File.exist?(File.join(@cdir, 'xyz.c')) + assert File.exist?(File.join(@cdir, 'x.c')) + end + + def create_test_data + verbose(false) do + + mkdir "testdata" unless File.exist? "testdata" + mkdir "testdata/CVS" rescue nil + mkdir "testdata/.svn" rescue nil + @cdir = "testdata/cfiles" + mkdir @cdir rescue nil + touch "testdata/.dummy" + touch "testdata/x.bak" + touch "testdata/x~" + touch "testdata/core" + touch "testdata/x.c" + touch "testdata/xyz.c" + touch "testdata/abc.c" + touch "testdata/abc.h" + touch "testdata/abc.x" + touch "testdata/existing" + end + end + +end diff --git a/test/rake/test_fileutils.rb b/test/rake/test_fileutils.rb new file mode 100644 index 0000000000..c32e505ecb --- /dev/null +++ b/test/rake/test_fileutils.rb @@ -0,0 +1,262 @@ +require 'rake' +require 'test/unit' +require_relative 'filecreation' +require 'fileutils' +require 'stringio' + +class TestFileUtils < Test::Unit::TestCase + include FileCreation + BASEDIR = File.dirname(__FILE__) + ShellCommand = "#{BASEDIR}/shellcommand.rb" + ENV_RUBY = ENV['RUBY'] + + def setup + if ruby = ENV_RUBY + @oldruby = FileUtils.class_eval {remove_const :RUBY} + FileUtils.class_eval {const_set(:RUBY, ruby)} + else + @oldruby = nil + end + end + + def teardown + FileUtils.rm_rf("testdata") + FileUtils::LN_SUPPORTED[0] = true + if @oldruby + ruby = @oldruby + FileUtils.class_eval {remove_const :RUBY} + FileUtils.class_eval {const_set(:RUBY, ruby)} + end + end + + def test_rm_one_file + create_file("testdata/a") + FileUtils.rm_rf "testdata/a" + assert ! File.exist?("testdata/a") + end + + def test_rm_two_files + create_file("testdata/a") + create_file("testdata/b") + FileUtils.rm_rf ["testdata/a", "testdata/b"] + assert ! File.exist?("testdata/a") + assert ! File.exist?("testdata/b") + end + + def test_rm_filelist + list = Rake::FileList.new << "testdata/a" << "testdata/b" + list.each { |fn| create_file(fn) } + FileUtils.rm_r list + assert ! File.exist?("testdata/a") + assert ! File.exist?("testdata/b") + end + + def test_ln + create_dir("testdata") + open("testdata/a", "w") { |f| f.puts "TEST_LN" } + RakeFileUtils.safe_ln("testdata/a", "testdata/b", :verbose => false) + assert_equal "TEST_LN\n", open("testdata/b") { |f| f.read } + end + + class BadLink + include RakeFileUtils + attr_reader :cp_args + def initialize(klass) + @failure_class = klass + end + def cp(*args) + @cp_args = args + end + def ln(*args) + fail @failure_class, "ln not supported" + end + public :safe_ln + end + + def test_safe_ln_failover_to_cp_on_standard_error + FileUtils::LN_SUPPORTED[0] = true + c = BadLink.new(StandardError) + c.safe_ln "a", "b" + assert_equal ['a', 'b'], c.cp_args + c.safe_ln "x", "y" + assert_equal ['x', 'y'], c.cp_args + end + + def test_safe_ln_failover_to_cp_on_not_implemented_error + FileUtils::LN_SUPPORTED[0] = true + c = BadLink.new(NotImplementedError) + c.safe_ln "a", "b" + assert_equal ['a', 'b'], c.cp_args + end + + def test_safe_ln_fails_on_script_error + FileUtils::LN_SUPPORTED[0] = true + c = BadLink.new(ScriptError) + assert_raise(ScriptError) do c.safe_ln "a", "b" end + end + + def test_verbose + verbose true + assert_equal true, verbose + verbose false + assert_equal false, verbose + verbose(true) { + assert_equal true, verbose + } + assert_equal false, verbose + end + + def test_nowrite + nowrite true + assert_equal true, nowrite + nowrite false + assert_equal false, nowrite + nowrite(true){ + assert_equal true, nowrite + } + assert_equal false, nowrite + end + + def test_file_utils_methods_are_available_at_top_level + create_file("testdata/a") + verbose(false) do + rm_rf "testdata/a" + end + assert ! File.exist?("testdata/a") + end + + def test_fileutils_methods_dont_leak + obj = Object.new + assert_raise(NoMethodError) { obj.copy } # from FileUtils + assert_raise(NoMethodError) { obj.ruby } # from RubyFileUtils + end + + def test_sh + verbose(false) { sh %{ruby #{ShellCommand}} } + assert true, "should not fail" + end + + # If the :sh method is invoked directly from a test unit instance + # (under mini/test), the mini/test version of fail is invoked rather + # than the kernel version of fail. So we run :sh from within a + # non-test class to avoid the problem. + class Sh + include FileUtils + def run(*args) + sh(*args) + end + def self.run(*args) + new.run(*args) + end + end + + def test_sh_with_a_single_string_argument + ENV['RAKE_TEST_SH'] = 'someval' + verbose(false) { + sh %{ruby #{BASEDIR}/check_expansion.rb #{env_var} someval} + } + end + + def test_sh_with_multiple_arguments + ENV['RAKE_TEST_SH'] = 'someval' + verbose(false) { + Sh.run 'ruby', File.expand_path('../check_no_expansion.rb', __FILE__), env_var, 'someval' + } + end + + def test_sh_failure + assert_raise(RuntimeError) { + verbose(false) { Sh.run "ruby #{File.expand_path('../shellcommand.rb', __FILE__)} 1" } + } + end + + def test_sh_special_handling + count = 0 + verbose(false) { + sh(%{ruby #{ShellCommand}}) do |ok, res| + assert(ok) + assert_equal 0, res.exitstatus + count += 1 + end + sh(%{ruby #{ShellCommand} 1}) do |ok, res| + assert(!ok) + assert_equal 1, res.exitstatus + count += 1 + end + } + assert_equal 2, count, "Block count should be 2" + end + + def test_sh_noop + verbose(false) { sh %{#{ShellCommand} 1}, :noop=>true } + assert true, "should not fail" + end + + def test_sh_bad_option + ex = assert_raise(ArgumentError) { + verbose(false) { sh %{#{ShellCommand}}, :bad_option=>true } + } + assert_match(/bad_option/, ex.message) + end + + def test_sh_verbose + out = redirect_stderr { + verbose(true) { + sh %{#{ShellCommand}}, :noop=>true + } + } + assert_match(/^#{Regexp.quote(ShellCommand)}$/o, out) + end + + def test_sh_no_verbose + out = redirect_stderr { + verbose(false) { + sh %{#{ShellCommand}}, :noop=>true + } + } + assert_equal '', out + end + + def test_ruby_with_a_single_string_argument + ENV['RAKE_TEST_SH'] = 'someval' + verbose(false) { + ruby %{#{BASEDIR}/check_expansion.rb #{env_var} someval} + } + end + + def test_ruby_with_multiple_arguments + ENV['RAKE_TEST_SH'] = 'someval' + verbose(false) { + ruby "#{BASEDIR}/check_no_expansion.rb", env_var, 'someval' + } + end + + def test_split_all + assert_equal ['a'], RakeFileUtils.split_all('a') + assert_equal ['..'], RakeFileUtils.split_all('..') + assert_equal ['/'], RakeFileUtils.split_all('/') + assert_equal ['a', 'b'], RakeFileUtils.split_all('a/b') + assert_equal ['/', 'a', 'b'], RakeFileUtils.split_all('/a/b') + assert_equal ['..', 'a', 'b'], RakeFileUtils.split_all('../a/b') + end + + private + + def redirect_stderr + old_err = $stderr + $stderr = StringIO.new + yield + $stderr.string + ensure + $stderr = old_err + end + + def windows? + ! File::ALT_SEPARATOR.nil? + end + + def env_var + windows? ? '%RAKE_TEST_SH%' : '$RAKE_TEST_SH' + end + +end diff --git a/test/rake/test_ftp.rb b/test/rake/test_ftp.rb new file mode 100644 index 0000000000..8b64890e3e --- /dev/null +++ b/test/rake/test_ftp.rb @@ -0,0 +1,57 @@ +require 'date' +require 'time' +require 'test/unit' +require 'rake/contrib/ftptools' + +class FakeDate + def self.today + Date.new(2003,10,3) + end + def self.now + Time.local(2003,10,3,12,00,00) + end +end + + +class TestFtpFile < Test::Unit::TestCase + + def setup + Rake::FtpFile.class_eval { @date_class = FakeDate; @time_class = FakeDate } + end + + def test_general + file = Rake::FtpFile.new("here", "-rw-r--r-- 1 a279376 develop 121770 Mar 6 14:50 wiki.pl") + assert_equal "wiki.pl", file.name + assert_equal "here/wiki.pl", file.path + assert_equal "a279376", file.owner + assert_equal "develop", file.group + assert_equal 0644, file.mode + assert_equal 121770, file.size + assert_equal Time.mktime(2003,3,6,14,50,0,0), file.time + assert ! file.directory? + assert ! file.symlink? + end + + def test_far_date + file = Rake::FtpFile.new(".", "drwxr-xr-x 3 a279376 develop 4096 Nov 26 2001 vss") + assert_equal Time.mktime(2001,11,26,0,0,0,0), file.time + end + + def test_close_date + file = Rake::FtpFile.new(".", "drwxr-xr-x 3 a279376 develop 4096 Nov 26 15:35 vss") + assert_equal Time.mktime(2002,11,26,15,35,0,0), file.time + end + + def test_directory + file = Rake::FtpFile.new(".", "drwxrwxr-x 9 a279376 develop 4096 Mar 13 14:32 working") + assert file.directory? + assert !file.symlink? + end + + def test_symlink + file = Rake::FtpFile.new(".", "lrwxrwxrwx 1 a279376 develop 64 Mar 26 2002 xtrac -> /home/a279376/working/ics/development/java/com/fmr/fwp/ics/xtrac") + assert_equal 'xtrac', file.name + assert file.symlink? + assert !file.directory? + end +end diff --git a/test/rake/test_invocation_chain.rb b/test/rake/test_invocation_chain.rb new file mode 100644 index 0000000000..a5843bfd2a --- /dev/null +++ b/test/rake/test_invocation_chain.rb @@ -0,0 +1,75 @@ +require 'test/unit' +require 'rake' + +###################################################################### +class TestAnEmptyInvocationChain < Test::Unit::TestCase + + def setup + @empty = Rake::InvocationChain::EMPTY + end + + def test_should_be_able_to_add_members + assert_nothing_raised do + @empty.append("A") + end + end + + def test_to_s + assert_equal "TOP", @empty.to_s + end +end + +###################################################################### +class TestAnInvocationChainWithOneMember < Test::Unit::TestCase + + def setup + @empty = Rake::InvocationChain::EMPTY + @first_member = "A" + @chain = @empty.append(@first_member) + end + + def test_should_report_first_member_as_a_member + assert @chain.member?(@first_member) + end + + def test_should_fail_when_adding_original_member + ex = assert_raise RuntimeError do + @chain.append(@first_member) + end + assert_match(/circular +dependency/i, ex.message) + assert_match(/A.*=>.*A/, ex.message) + end + + def test_to_s + assert_equal "TOP => A", @chain.to_s + end + +end + +###################################################################### +class TestAnInvocationChainWithMultipleMember < Test::Unit::TestCase + + def setup + @first_member = "A" + @second_member = "B" + ch = Rake::InvocationChain::EMPTY.append(@first_member) + @chain = ch.append(@second_member) + end + + def test_should_report_first_member_as_a_member + assert @chain.member?(@first_member) + end + + def test_should_report_second_member_as_a_member + assert @chain.member?(@second_member) + end + + def test_should_fail_when_adding_original_member + ex = assert_raise RuntimeError do + @chain.append(@first_member) + end + assert_match(/A.*=>.*B.*=>.*A/, ex.message) + end +end + + diff --git a/test/rake/test_makefile_loader.rb b/test/rake/test_makefile_loader.rb new file mode 100644 index 0000000000..69e09e1da3 --- /dev/null +++ b/test/rake/test_makefile_loader.rb @@ -0,0 +1,24 @@ +require 'test/unit' +require 'rake' +require 'rake/loaders/makefile' + +class TestMakefileLoader < Test::Unit::TestCase + include Rake + + def test_parse + Task.clear + loader = Rake::MakefileLoader.new + loader.load("#{File.dirname(__FILE__)}/data/sample.mf") + %w(a b c d).each do |t| + assert Task.task_defined?(t), "#{t} should be a defined task" + end + assert_equal %w(a1 a2 a3 a4 a5 a6 a7).sort, Task['a'].prerequisites.sort + assert_equal %w(b1 b2 b3 b4 b5 b6 b7).sort, Task['b'].prerequisites.sort + assert_equal %w(c1).sort, Task['c'].prerequisites.sort + assert_equal %w(d1 d2).sort, Task['d'].prerequisites.sort + assert_equal %w(e1 f1).sort, Task['e'].prerequisites.sort + assert_equal %w(e1 f1).sort, Task['f'].prerequisites.sort + assert_equal ["g1", "g 2", "g 3", "g4"].sort, Task['g 0'].prerequisites.sort + assert_equal 7, Task.tasks.size + end +end diff --git a/test/rake/test_multitask.rb b/test/rake/test_multitask.rb new file mode 100644 index 0000000000..d1178e6765 --- /dev/null +++ b/test/rake/test_multitask.rb @@ -0,0 +1,43 @@ +require 'test/unit' +require 'rake' + +###################################################################### +class TestMultiTask < Test::Unit::TestCase + include Rake + + def setup + Task.clear + @runs = Array.new + end + + def test_running_multitasks + task :a do 3.times do |i| @runs << "A#{i}"; sleep 0.01; end end + task :b do 3.times do |i| @runs << "B#{i}"; sleep 0.01; end end + multitask :both => [:a, :b] + Task[:both].invoke + assert_equal 6, @runs.size + assert @runs.index("A0") < @runs.index("A1") + assert @runs.index("A1") < @runs.index("A2") + assert @runs.index("B0") < @runs.index("B1") + assert @runs.index("B1") < @runs.index("B2") + end + + def test_all_multitasks_wait_on_slow_prerequisites + task :slow do 3.times do |i| @runs << "S#{i}"; sleep 0.05 end end + task :a => [:slow] do 3.times do |i| @runs << "A#{i}"; sleep 0.01 end end + task :b => [:slow] do 3.times do |i| @runs << "B#{i}"; sleep 0.01 end end + multitask :both => [:a, :b] + Task[:both].invoke + assert_equal 9, @runs.size + assert @runs.index("S0") < @runs.index("S1") + assert @runs.index("S1") < @runs.index("S2") + assert @runs.index("S2") < @runs.index("A0") + assert @runs.index("S2") < @runs.index("B0") + assert @runs.index("A0") < @runs.index("A1") + assert @runs.index("A1") < @runs.index("A2") + assert @runs.index("B0") < @runs.index("B1") + assert @runs.index("B1") < @runs.index("B2") + end +end + + diff --git a/test/rake/test_namespace.rb b/test/rake/test_namespace.rb new file mode 100755 index 0000000000..30608de122 --- /dev/null +++ b/test/rake/test_namespace.rb @@ -0,0 +1,44 @@ +require 'test/unit' +require 'rake' + +class TestNameSpace < Test::Unit::TestCase + + class TM + include Rake::TaskManager + end + + def test_namespace_creation + mgr = TM.new + ns = Rake::NameSpace.new(mgr, []) + assert_not_nil ns + end + + def test_namespace_lookup + mgr = TM.new + ns = mgr.in_namespace("n") do + mgr.define_task(Rake::Task, "t") + end + + assert_not_nil ns["t"] + assert_equal mgr["n:t"], ns["t"] + end + + def test_namespace_reports_tasks_it_owns + mgr = TM.new + nns = nil + ns = mgr.in_namespace("n") do + mgr.define_task(Rake::Task, :x) + mgr.define_task(Rake::Task, :y) + nns = mgr.in_namespace("nn") do + mgr.define_task(Rake::Task, :z) + end + end + mgr.in_namespace("m") do + mgr.define_task(Rake::Task, :x) + end + + assert_equal ["n:nn:z", "n:x", "n:y"], + ns.tasks.map { |tsk| tsk.name } + assert_equal ["n:nn:z"], nns.tasks.map {|t| t.name} + end +end diff --git a/test/rake/test_package_task.rb b/test/rake/test_package_task.rb new file mode 100644 index 0000000000..cce09fffb6 --- /dev/null +++ b/test/rake/test_package_task.rb @@ -0,0 +1,105 @@ +require 'test/unit' +require 'rake/packagetask' + +class TestPackageTask < Test::Unit::TestCase + include Rake + + def test_create + pkg = Rake::PackageTask.new("pkgr", "1.2.3") { |p| + p.package_files << "install.rb" + p.package_files.include( + '[A-Z]*', + 'bin/**/*', + 'lib/**/*.rb', + 'test/**/*.rb', + 'doc/**/*', + 'build/rubyapp.rb', + '*.blurb') + p.package_files.exclude(/\bCVS\b/) + p.package_files.exclude(/~$/) + p.package_dir = 'pkg' + p.need_tar = true + p.need_tar_gz = true + p.need_tar_bz2 = true + p.need_zip = true + } + assert_equal "pkg", pkg.package_dir + assert pkg.package_files.include?("bin/rake") + assert "pkgr", pkg.name + assert "1.2.3", pkg.version + assert Task[:package] + assert Task['pkg/pkgr-1.2.3.tgz'] + assert Task['pkg/pkgr-1.2.3.tar.gz'] + assert Task['pkg/pkgr-1.2.3.tar.bz2'] + assert Task['pkg/pkgr-1.2.3.zip'] + assert Task["pkg/pkgr-1.2.3"] + assert Task[:clobber_package] + assert Task[:repackage] + end + + def test_missing_version + assert_raise(RuntimeError) { + pkg = Rake::PackageTask.new("pkgr") { |p| } + } + end + + def test_no_version + pkg = Rake::PackageTask.new("pkgr", :noversion) { |p| } + assert "pkgr", pkg.send(:package_name) + end + + def test_clone + pkg = Rake::PackageTask.new("x", :noversion) + p2 = pkg.clone + pkg.package_files << "y" + p2.package_files << "x" + assert_equal ["y"], pkg.package_files + assert_equal ["x"], p2.package_files + end +end + + +require 'rake/gempackagetask' + +class TestGemPackageTask < Test::Unit::TestCase + def test_gem_package + gem = Gem::Specification.new do |g| + g.name = "pkgr" + g.version = "1.2.3" + g.files = FileList["x"].resolve + end + pkg = Rake::GemPackageTask.new(gem) do |p| + p.package_files << "y" + end + assert_equal ["x", "y"], pkg.package_files + assert_equal "pkgr-1.2.3.gem", pkg.gem_file + end + + def test_gem_package_with_current_platform + gem = Gem::Specification.new do |g| + g.name = "pkgr" + g.version = "1.2.3" + g.files = FileList["x"].resolve + g.platform = Gem::Platform::CURRENT + end + pkg = Rake::GemPackageTask.new(gem) do |p| + p.package_files << "y" + end + assert_equal ["x", "y"], pkg.package_files + assert_match(/^pkgr-1\.2\.3-(\S+)\.gem$/, pkg.gem_file) + end + + def test_gem_package_with_ruby_platform + gem = Gem::Specification.new do |g| + g.name = "pkgr" + g.version = "1.2.3" + g.files = FileList["x"].resolve + g.platform = Gem::Platform::RUBY + end + pkg = Rake::GemPackageTask.new(gem) do |p| + p.package_files << "y" + end + assert_equal ["x", "y"], pkg.package_files + assert_equal "pkgr-1.2.3.gem", pkg.gem_file + end +end diff --git a/test/rake/test_pathmap.rb b/test/rake/test_pathmap.rb new file mode 100644 index 0000000000..3e9935f9ba --- /dev/null +++ b/test/rake/test_pathmap.rb @@ -0,0 +1,207 @@ +require 'test/unit' +require 'rake' + +# ==================================================================== +class TestPathMap < Test::Unit::TestCase + + def test_returns_self_with_no_args + assert_equal "abc.rb", "abc.rb".pathmap + end + + def test_s_returns_file_separator + sep = File::ALT_SEPARATOR || File::SEPARATOR + assert_equal sep, "abc.rb".pathmap("%s") + assert_equal sep, "".pathmap("%s") + assert_equal "a#{sep}b", "a/b".pathmap("%d%s%f") + end + + def test_f_returns_basename + assert_equal "abc.rb", "abc.rb".pathmap("%f") + assert_equal "abc.rb", "this/is/a/dir/abc.rb".pathmap("%f") + assert_equal "abc.rb", "/this/is/a/dir/abc.rb".pathmap("%f") + end + + def test_n_returns_basename_without_extension + assert_equal "abc", "abc.rb".pathmap("%n") + assert_equal "abc", "abc".pathmap("%n") + assert_equal "abc", "this/is/a/dir/abc.rb".pathmap("%n") + assert_equal "abc", "/this/is/a/dir/abc.rb".pathmap("%n") + assert_equal "abc", "/this/is/a/dir/abc".pathmap("%n") + end + + def test_d_returns_dirname + assert_equal ".", "abc.rb".pathmap("%d") + assert_equal "/", "/abc".pathmap("%d") + assert_equal "this/is/a/dir", "this/is/a/dir/abc.rb".pathmap("%d") + assert_equal "/this/is/a/dir", "/this/is/a/dir/abc.rb".pathmap("%d") + end + + def test_9d_returns_partial_dirname + assert_equal "this/is", "this/is/a/dir/abc.rb".pathmap("%2d") + assert_equal "this", "this/is/a/dir/abc.rb".pathmap("%1d") + assert_equal ".", "this/is/a/dir/abc.rb".pathmap("%0d") + assert_equal "dir", "this/is/a/dir/abc.rb".pathmap("%-1d") + assert_equal "a/dir", "this/is/a/dir/abc.rb".pathmap("%-2d") + assert_equal "this/is/a/dir", "this/is/a/dir/abc.rb".pathmap("%100d") + assert_equal "this/is/a/dir", "this/is/a/dir/abc.rb".pathmap("%-100d") + end + + def test_x_returns_extension + assert_equal "", "abc".pathmap("%x") + assert_equal ".rb", "abc.rb".pathmap("%x") + assert_equal ".rb", "abc.xyz.rb".pathmap("%x") + assert_equal "", ".depends".pathmap("%x") + assert_equal "", "dir/.depends".pathmap("%x") + end + + def test_X_returns_everything_but_extension + assert_equal "abc", "abc".pathmap("%X") + assert_equal "abc", "abc.rb".pathmap("%X") + assert_equal "abc.xyz", "abc.xyz.rb".pathmap("%X") + assert_equal "ab.xyz", "ab.xyz.rb".pathmap("%X") + assert_equal "a.xyz", "a.xyz.rb".pathmap("%X") + assert_equal "abc", "abc.rb".pathmap("%X") + assert_equal "ab", "ab.rb".pathmap("%X") + assert_equal "a", "a.rb".pathmap("%X") + assert_equal ".depends", ".depends".pathmap("%X") + assert_equal "a/dir/.depends", "a/dir/.depends".pathmap("%X") + assert_equal "/.depends", "/.depends".pathmap("%X") + end + + def test_p_returns_entire_pathname + assert_equal "abc.rb", "abc.rb".pathmap("%p") + assert_equal "this/is/a/dir/abc.rb", "this/is/a/dir/abc.rb".pathmap("%p") + assert_equal "/this/is/a/dir/abc.rb", "/this/is/a/dir/abc.rb".pathmap("%p") + end + + def test_dash_returns_empty_string + assert_equal "", "abc.rb".pathmap("%-") + assert_equal "abc.rb", "abc.rb".pathmap("%X%-%x") + end + + def test_percent_percent_returns_percent + assert_equal "a%b", "".pathmap("a%%b") + end + + def test_undefined_percent_causes_error + ex = assert_raise(ArgumentError) { + "dir/abc.rb".pathmap("%z") + } + end + + def test_pattern_returns_substitutions + assert_equal "bin/org/osb", + "src/org/osb/Xyz.java".pathmap("%{src,bin}d") + end + + def test_pattern_can_use_backreferences + assert_equal "dir/hi/is", "dir/this/is".pathmap("%{t(hi)s,\\1}p") + end + + def test_pattern_with_star_replacement_string_uses_block + assert_equal "src/ORG/osb", + "src/org/osb/Xyz.java".pathmap("%{/org,*}d") { |d| d.upcase } + assert_equal "Xyz.java", + "src/org/osb/Xyz.java".pathmap("%{.*,*}f") { |f| f.capitalize } + end + + def test_pattern_with_no_replacement_nor_block_substitutes_empty_string + assert_equal "bc.rb", "abc.rb".pathmap("%{a}f") + end + + def test_pattern_works_with_certain_valid_operators + assert_equal "dir/xbc.rb", "dir/abc.rb".pathmap("%{a,x}p") + assert_equal "d1r", "dir/abc.rb".pathmap("%{i,1}d") + assert_equal "xbc.rb", "dir/abc.rb".pathmap("%{a,x}f") + assert_equal ".Rb", "dir/abc.rb".pathmap("%{r,R}x") + assert_equal "xbc", "dir/abc.rb".pathmap("%{a,x}n") + end + + def test_multiple_patterns + assert_equal "this/is/b/directory/abc.rb", + "this/is/a/dir/abc.rb".pathmap("%{a,b;dir,\\0ectory}p") + end + + def test_partial_directory_selection_works_with_patterns + assert_equal "this/is/a/long", + "this/is/a/really/long/path/ok.rb".pathmap("%{/really/,/}5d") + end + + def test_pattern_with_invalid_operator + ex = assert_raise(ArgumentError) do + "abc.xyz".pathmap("%{src,bin}z") + end + assert_match(/unknown.*pathmap.*spec.*z/i, ex.message) + end + + def test_works_with_windows_separators + if File::ALT_SEPARATOR + assert_equal "abc", 'dir\abc.rb'.pathmap("%n") + assert_equal 'this\is\a\dir', + 'this\is\a\dir\abc.rb'.pathmap("%d") + end + end + + def test_complex_patterns + sep = "".pathmap("%s") + assert_equal "dir/abc.rb", "dir/abc.rb".pathmap("%d/%n%x") + assert_equal "./abc.rb", "abc.rb".pathmap("%d/%n%x") + assert_equal "Your file extension is '.rb'", + "dir/abc.rb".pathmap("Your file extension is '%x'") + assert_equal "bin/org/onstepback/proj/A.class", + "src/org/onstepback/proj/A.java".pathmap("%{src,bin}d/%n.class") + assert_equal "src_work/bin/org/onstepback/proj/A.class", + "src_work/src/org/onstepback/proj/A.java".pathmap('%{\bsrc\b,bin}X.class') + assert_equal ".depends.bak", ".depends".pathmap("%X.bak") + assert_equal "d#{sep}a/b/c#{sep}file.txt", "a/b/c/d/file.txt".pathmap("%-1d%s%3d%s%f") + end +end + +class TestPathMapExplode < Test::Unit::TestCase + def setup + String.class_eval { public :pathmap_explode } + end + + def teardown + String.class_eval { protected :pathmap_explode } + end + + def test_explode + assert_equal ['a'], 'a'.pathmap_explode + assert_equal ['a', 'b'], 'a/b'.pathmap_explode + assert_equal ['a', 'b', 'c'], 'a/b/c'.pathmap_explode + assert_equal ['/', 'a'], '/a'.pathmap_explode + assert_equal ['/', 'a', 'b'], '/a/b'.pathmap_explode + assert_equal ['/', 'a', 'b', 'c'], '/a/b/c'.pathmap_explode + if File::ALT_SEPARATOR + assert_equal ['c:.', 'a'], 'c:a'.pathmap_explode + assert_equal ['c:.', 'a', 'b'], 'c:a/b'.pathmap_explode + assert_equal ['c:.', 'a', 'b', 'c'], 'c:a/b/c'.pathmap_explode + assert_equal ['c:/', 'a'], 'c:/a'.pathmap_explode + assert_equal ['c:/', 'a', 'b'], 'c:/a/b'.pathmap_explode + assert_equal ['c:/', 'a', 'b', 'c'], 'c:/a/b/c'.pathmap_explode + end + end +end + +class TestPathMapPartial < Test::Unit::TestCase + def test_pathmap_partial + @path = "1/2/file" + def @path.call(n) + pathmap_partial(n) + end + assert_equal("1", @path.call(1)) + assert_equal("1/2", @path.call(2)) + assert_equal("1/2", @path.call(3)) + assert_equal(".", @path.call(0)) + assert_equal("2", @path.call(-1)) + assert_equal("1/2", @path.call(-2)) + assert_equal("1/2", @path.call(-3)) + end +end + +class TestFileListPathMap < Test::Unit::TestCase + def test_file_list_supports_pathmap + assert_equal ['a', 'b'], FileList['dir/a.rb', 'dir/b.rb'].pathmap("%n") + end +end diff --git a/test/rake/test_pseudo_status.rb b/test/rake/test_pseudo_status.rb new file mode 100644 index 0000000000..149aa5bf9f --- /dev/null +++ b/test/rake/test_pseudo_status.rb @@ -0,0 +1,23 @@ +require 'test/unit' +require 'rake' + +require_relative 'capture_stdout' + +class PseudoStatusTest < Test::Unit::TestCase + def test_with_zero_exit_status + s = Rake::PseudoStatus.new + assert_equal 0, s.exitstatus + assert_equal 0, s.to_i + assert_equal 0, s >> 8 + assert ! s.stopped? + assert s.exited? + end + def test_with_99_exit_status + s = Rake::PseudoStatus.new(99) + assert_equal 99, s.exitstatus + assert_equal 25344, s.to_i + assert_equal 99, s >> 8 + assert ! s.stopped? + assert s.exited? + end +end diff --git a/test/rake/test_rake.rb b/test/rake/test_rake.rb new file mode 100644 index 0000000000..0f0f6a843d --- /dev/null +++ b/test/rake/test_rake.rb @@ -0,0 +1,39 @@ +require 'test/unit' +require 'rake' + +class TestRake < Test::Unit::TestCase + def test_each_dir_parent + assert_equal ['a'], alldirs('a') + assert_equal ['a/b', 'a'], alldirs('a/b') + assert_equal ['/a/b', '/a', '/'], alldirs('/a/b') + if File.dirname("c:/foo") == "c:" + # Under Unix + assert_equal ['c:/a/b', 'c:/a', 'c:'], alldirs('c:/a/b') + assert_equal ['c:a/b', 'c:a'], alldirs('c:a/b') + else + # Under Windows + assert_equal ['c:/a/b', 'c:/a', 'c:/'], alldirs('c:/a/b') + assert_equal ['c:a/b', 'c:a'], alldirs('c:a/b') + end + end + + def alldirs(fn) + result = [] + Rake.each_dir_parent(fn) { |d| result << d } + result + end + + def test_can_override_application + old_app = Rake.application + fake_app = Object.new + Rake.application = fake_app + assert_equal fake_app, Rake.application + ensure + Rake.application = old_app + end + + def test_original_dir_reports_current_dir + assert_equal Dir.pwd, Rake.original_dir + end + +end diff --git a/test/rake/test_rdoc_task.rb b/test/rake/test_rdoc_task.rb new file mode 100644 index 0000000000..524057cf07 --- /dev/null +++ b/test/rake/test_rdoc_task.rb @@ -0,0 +1,84 @@ +require 'test/unit' +require 'rake/rdoctask' + +class TestRDocTask < Test::Unit::TestCase + include Rake + + def setup + Task.clear + end + + def test_tasks_creation + Rake::RDocTask.new + assert Task[:rdoc] + assert Task[:clobber_rdoc] + assert Task[:rerdoc] + end + + def test_tasks_creation_with_custom_name_symbol + rd = Rake::RDocTask.new(:rdoc_dev) + assert Task[:rdoc_dev] + assert Task[:clobber_rdoc_dev] + assert Task[:rerdoc_dev] + assert_equal :rdoc_dev, rd.name + end + + def test_tasks_creation_with_custom_name_string + rd = Rake::RDocTask.new("rdoc_dev") + assert Task[:rdoc_dev] + assert Task[:clobber_rdoc_dev] + assert Task[:rerdoc_dev] + assert_equal "rdoc_dev", rd.name + end + + def test_tasks_creation_with_custom_name_hash + options = { :rdoc => "rdoc", :clobber_rdoc => "rdoc:clean", :rerdoc => "rdoc:force" } + rd = Rake::RDocTask.new(options) + assert Task[:"rdoc"] + assert Task[:"rdoc:clean"] + assert Task[:"rdoc:force"] + assert_raises(RuntimeError) { Task[:clobber_rdoc] } + assert_equal options, rd.name + end + + def test_tasks_creation_with_custom_name_hash_will_use_default_if_an_option_isnt_given + rd = Rake::RDocTask.new(:clobber_rdoc => "rdoc:clean") + assert Task[:rdoc] + assert Task[:"rdoc:clean"] + assert Task[:rerdoc] + end + + def test_tasks_creation_with_custom_name_hash_raises_exception_if_invalid_option_given + assert_raises(ArgumentError) do + Rake::RDocTask.new(:foo => "bar") + end + + begin + Rake::RDocTask.new(:foo => "bar") + rescue ArgumentError => e + assert_match(/foo/, e.message) + end + end + + def test_inline_source_is_enabled_by_default + rd = Rake::RDocTask.new + assert rd.option_list.include?('--inline-source') + end + + def test_inline_source_option_is_only_appended_if_option_not_already_given + rd = Rake::RDocTask.new + rd.options << '--inline-source' + assert_equal 1, rd.option_list.grep('--inline-source').size + + rd = Rake::RDocTask.new + rd.options << '-S' + assert_equal 1, rd.option_list.grep('-S').size + assert_equal 0, rd.option_list.grep('--inline-source').size + end + + def test_inline_source_option_can_be_disabled + rd = Rake::RDocTask.new + rd.inline_source = false + assert !rd.option_list.include?('--inline-source') + end +end diff --git a/test/rake/test_require.rb b/test/rake/test_require.rb new file mode 100644 index 0000000000..236b992f78 --- /dev/null +++ b/test/rake/test_require.rb @@ -0,0 +1,32 @@ +require 'test/unit' +require 'rake' + +# ==================================================================== +class TestRequire < Test::Unit::TestCase + RakeLibDir = File.dirname(__FILE__) + '/data/rakelib' + + def test_can_load_rake_library + app = Rake::Application.new + assert app.instance_eval { + rake_require("test1", [RakeLibDir], []) + } + end + + def test_wont_reload_rake_library + app = Rake::Application.new + assert ! app.instance_eval { + rake_require("test2", [RakeLibDir], ['test2']) + } + end + + def test_throws_error_if_library_not_found + app = Rake::Application.new + ex = assert_raise(LoadError) { + assert app.instance_eval { + rake_require("testx", [RakeLibDir], []) + } + } + assert_match(/x/, ex.message) + end +end + diff --git a/test/rake/test_rules.rb b/test/rake/test_rules.rb new file mode 100644 index 0000000000..4dbf75d1f0 --- /dev/null +++ b/test/rake/test_rules.rb @@ -0,0 +1,345 @@ +require 'test/unit' +require 'fileutils' +require 'rake' +require_relative 'filecreation' + +###################################################################### +class TestRules < Test::Unit::TestCase + include Rake + include FileCreation + + SRCFILE = "testdata/abc.c" + SRCFILE2 = "testdata/xyz.c" + FTNFILE = "testdata/abc.f" + OBJFILE = "testdata/abc.o" + FOOFILE = "testdata/foo" + DOTFOOFILE = "testdata/.foo" + + def setup + Task.clear + @runs = [] + end + + def teardown + FileList['testdata/*'].uniq.each do |f| rm_r(f, :verbose=>false) end + end + + def test_multiple_rules1 + create_file(FTNFILE) + delete_file(SRCFILE) + delete_file(OBJFILE) + rule(/\.o$/ => ['.c']) do @runs << :C end + rule(/\.o$/ => ['.f']) do @runs << :F end + t = Task[OBJFILE] + t.invoke + Task[OBJFILE].invoke + assert_equal [:F], @runs + end + + def test_multiple_rules2 + create_file(FTNFILE) + delete_file(SRCFILE) + delete_file(OBJFILE) + rule(/\.o$/ => ['.f']) do @runs << :F end + rule(/\.o$/ => ['.c']) do @runs << :C end + Task[OBJFILE].invoke + assert_equal [:F], @runs + end + + def test_create_with_source + create_file(SRCFILE) + rule(/\.o$/ => ['.c']) do |t| + @runs << t.name + assert_equal OBJFILE, t.name + assert_equal SRCFILE, t.source + end + Task[OBJFILE].invoke + assert_equal [OBJFILE], @runs + end + + def test_single_dependent + create_file(SRCFILE) + rule(/\.o$/ => '.c') do |t| + @runs << t.name + end + Task[OBJFILE].invoke + assert_equal [OBJFILE], @runs + end + + def test_rule_can_be_created_by_string + create_file(SRCFILE) + rule '.o' => ['.c'] do |t| + @runs << t.name + end + Task[OBJFILE].invoke + assert_equal [OBJFILE], @runs + end + + def test_rule_prereqs_can_be_created_by_string + create_file(SRCFILE) + rule '.o' => '.c' do |t| + @runs << t.name + end + Task[OBJFILE].invoke + assert_equal [OBJFILE], @runs + end + + def test_plain_strings_as_dependents_refer_to_files + create_file(SRCFILE) + rule '.o' => SRCFILE do |t| + @runs << t.name + end + Task[OBJFILE].invoke + assert_equal [OBJFILE], @runs + end + + def test_file_names_beginning_with_dot_can_be_tricked_into_refering_to_file + verbose(false) do + chdir("testdata") do + create_file('.foo') + rule '.o' => "./.foo" do |t| + @runs << t.name + end + Task[OBJFILE].invoke + assert_equal [OBJFILE], @runs + end + end + end + + def test_file_names_beginning_with_dot_can_be_wrapped_in_lambda + verbose(false) do + chdir("testdata") do + create_file(".foo") + rule '.o' => lambda{".foo"} do |t| + @runs << "#{t.name} - #{t.source}" + end + Task[OBJFILE].invoke + assert_equal ["#{OBJFILE} - .foo"], @runs + end + end + end + + def test_file_names_containing_percent_can_be_wrapped_in_lambda + verbose(false) do + chdir("testdata") do + create_file("foo%x") + rule '.o' => lambda{"foo%x"} do |t| + @runs << "#{t.name} - #{t.source}" + end + Task[OBJFILE].invoke + assert_equal ["#{OBJFILE} - foo%x"], @runs + end + end + end + + def test_non_extension_rule_name_refers_to_file + verbose(false) do + chdir("testdata") do + create_file("abc.c") + rule "abc" => '.c' do |t| + @runs << t.name + end + Task["abc"].invoke + assert_equal ["abc"], @runs + end + end + end + + def test_pathmap_automatically_applies_to_name + verbose(false) do + chdir("testdata") do + create_file("zzabc.c") + rule ".o" => 'zz%{x,a}n.c' do |t| + @runs << "#{t.name} - #{t.source}" + end + Task["xbc.o"].invoke + assert_equal ["xbc.o - zzabc.c"], @runs + end + end + end + + def test_plain_strings_are_just_filenames + verbose(false) do + chdir("testdata") do + create_file("plainname") + rule ".o" => 'plainname' do |t| + @runs << "#{t.name} - #{t.source}" + end + Task["xbc.o"].invoke + assert_equal ["xbc.o - plainname"], @runs + end + end + end + + def test_rule_runs_when_explicit_task_has_no_actions + create_file(SRCFILE) + create_file(SRCFILE2) + delete_file(OBJFILE) + rule '.o' => '.c' do |t| + @runs << t.source + end + file OBJFILE => [SRCFILE2] + Task[OBJFILE].invoke + assert_equal [SRCFILE], @runs + end + + def test_close_matches_on_name_do_not_trigger_rule + create_file("testdata/x.c") + rule '.o' => ['.c'] do |t| + @runs << t.name + end + assert_raise(RuntimeError) { Task['testdata/x.obj'].invoke } + assert_raise(RuntimeError) { Task['testdata/x.xyo'].invoke } + end + + def test_rule_rebuilds_obj_when_source_is_newer + create_timed_files(OBJFILE, SRCFILE) + rule(/\.o$/ => ['.c']) do + @runs << :RULE + end + Task[OBJFILE].invoke + assert_equal [:RULE], @runs + end + + def test_rule_with_two_sources_runs_if_both_sources_are_present + create_timed_files(OBJFILE, SRCFILE, SRCFILE2) + rule OBJFILE => [lambda{SRCFILE}, lambda{SRCFILE2}] do + @runs << :RULE + end + Task[OBJFILE].invoke + assert_equal [:RULE], @runs + end + + def test_rule_with_two_sources_but_one_missing_does_not_run + create_timed_files(OBJFILE, SRCFILE) + delete_file(SRCFILE2) + rule OBJFILE => [lambda{SRCFILE}, lambda{SRCFILE2}] do + @runs << :RULE + end + Task[OBJFILE].invoke + assert_equal [], @runs + end + + def test_rule_with_two_sources_builds_both_sources + task 'x.aa' + task 'x.bb' + rule '.a' => '.aa' do + @runs << "A" + end + rule '.b' => '.bb' do + @runs << "B" + end + rule ".c" => ['.a', '.b'] do + @runs << "C" + end + Task["x.c"].invoke + assert_equal ["A", "B", "C"], @runs.sort + end + + def test_second_rule_runs_when_first_rule_doesnt + create_timed_files(OBJFILE, SRCFILE) + delete_file(SRCFILE2) + rule OBJFILE => [lambda{SRCFILE}, lambda{SRCFILE2}] do + @runs << :RULE1 + end + rule OBJFILE => [lambda{SRCFILE}] do + @runs << :RULE2 + end + Task[OBJFILE].invoke + assert_equal [:RULE2], @runs + end + + def test_second_rule_doest_run_if_first_triggers + create_timed_files(OBJFILE, SRCFILE, SRCFILE2) + rule OBJFILE => [lambda{SRCFILE}, lambda{SRCFILE2}] do + @runs << :RULE1 + end + rule OBJFILE => [lambda{SRCFILE}] do + @runs << :RULE2 + end + Task[OBJFILE].invoke + assert_equal [:RULE1], @runs + end + + def test_second_rule_doest_run_if_first_triggers_with_reversed_rules + create_timed_files(OBJFILE, SRCFILE, SRCFILE2) + rule OBJFILE => [lambda{SRCFILE}] do + @runs << :RULE1 + end + rule OBJFILE => [lambda{SRCFILE}, lambda{SRCFILE2}] do + @runs << :RULE2 + end + Task[OBJFILE].invoke + assert_equal [:RULE1], @runs + end + + def test_rule_with_proc_dependent_will_trigger + ran = false + mkdir_p("testdata/src/jw") + create_file("testdata/src/jw/X.java") + rule %r(classes/.*\.class) => [ + proc { |fn| fn.pathmap("%{classes,testdata/src}d/%n.java") } + ] do |task| + assert_equal task.name, 'classes/jw/X.class' + assert_equal task.source, 'testdata/src/jw/X.java' + @runs << :RULE + end + Task['classes/jw/X.class'].invoke + assert_equal [:RULE], @runs + ensure + rm_r("testdata/src", :verbose=>false) rescue nil + end + + def test_proc_returning_lists_are_flattened_into_prereqs + ran = false + mkdir_p("testdata/flatten") + create_file("testdata/flatten/a.txt") + task 'testdata/flatten/b.data' do |t| + ran = true + touch t.name, :verbose => false + end + rule '.html' => + proc { |fn| + [ + fn.ext("txt"), + "testdata/flatten/b.data" + ] + } do |task| + end + Task['testdata/flatten/a.html'].invoke + assert ran, "Should have triggered flattened dependency" + ensure + rm_r("testdata/flatten", :verbose=>false) rescue nil + end + + def test_recursive_rules_will_work_as_long_as_they_terminate + actions = [] + create_file("testdata/abc.xml") + rule '.y' => '.xml' do actions << 'y' end + rule '.c' => '.y' do actions << 'c'end + rule '.o' => '.c' do actions << 'o'end + rule '.exe' => '.o' do actions << 'exe'end + Task["testdata/abc.exe"].invoke + assert_equal ['y', 'c', 'o', 'exe'], actions + end + + def test_recursive_rules_that_dont_terminate_will_overflow + create_file("testdata/a.a") + prev = 'a' + ('b'..'z').each do |letter| + rule ".#{letter}" => ".#{prev}" do |t| puts "#{t.name}" end + prev = letter + end + ex = assert_raise(Rake::RuleRecursionOverflowError) { + Task["testdata/a.z"].invoke + } + assert_match(/a\.z => testdata\/a.y/, ex.message) + end + + def test_rules_with_bad_dependents_will_fail + rule "a" => [ 1 ] do |t| puts t.name end + assert_raise(RuntimeError) do Task['a'].invoke end + end + +end + diff --git a/test/rake/test_task_arguments.rb b/test/rake/test_task_arguments.rb new file mode 100644 index 0000000000..daecbcf730 --- /dev/null +++ b/test/rake/test_task_arguments.rb @@ -0,0 +1,87 @@ +require 'test/unit' +require 'rake' + +###################################################################### +class TestTaskArguments < Test::Unit::TestCase + def teardown + ENV.delete('rev') + ENV.delete('VER') + end + + def test_empty_arg_list_is_empty + ta = Rake::TaskArguments.new([], []) + assert_equal({}, ta.to_hash) + end + + def test_multiple_values_in_args + ta = Rake::TaskArguments.new([:a, :b, :c], [:one, :two, :three]) + assert_equal({:a => :one, :b => :two, :c => :three}, ta.to_hash) + end + + def test_to_s + ta = Rake::TaskArguments.new([:a, :b, :c], [1, 2, 3]) + assert_equal ta.to_hash.inspect, ta.to_s + assert_equal ta.to_hash.inspect, ta.inspect + end + + def test_enumerable_behavior + ta = Rake::TaskArguments.new([:a, :b, :c], [1, 2 ,3]) + assert_equal [10, 20, 30], ta.collect { |k,v| v * 10 }.sort + end + + def test_named_args + ta = Rake::TaskArguments.new(["aa", "bb"], [1, 2]) + assert_equal 1, ta.aa + assert_equal 1, ta[:aa] + assert_equal 1, ta["aa"] + assert_equal 2, ta.bb + assert_nil ta.cc + end + + def test_args_knows_its_names + ta = Rake::TaskArguments.new(["aa", "bb"], [1, 2]) + assert_equal ["aa", "bb"], ta.names + end + + def test_extra_names_are_nil + ta = Rake::TaskArguments.new(["aa", "bb", "cc"], [1, 2]) + assert_nil ta.cc + end + + def test_args_can_reference_env_values + ta = Rake::TaskArguments.new(["aa"], [1]) + ENV['rev'] = "1.2" + ENV['VER'] = "2.3" + assert_equal "1.2", ta.rev + assert_equal "2.3", ta.ver + end + + def test_creating_new_argument_scopes + parent = Rake::TaskArguments.new(['p'], [1]) + child = parent.new_scope(['c', 'p']) + assert_equal({:p=>1}, child.to_hash) + assert_equal 1, child.p + assert_equal 1, child["p"] + assert_equal 1, child[:p] + assert_nil child.c + end + + def test_child_hides_parent_arg_names + parent = Rake::TaskArguments.new(['aa'], [1]) + child = Rake::TaskArguments.new(['aa'], [2], parent) + assert_equal 2, child.aa + end + + def test_default_arguments_values_can_be_merged + ta = Rake::TaskArguments.new(["aa", "bb"], [nil, "original_val"]) + ta.with_defaults({ :aa => 'default_val' }) + assert_equal 'default_val', ta[:aa] + assert_equal 'original_val', ta[:bb] + end + + def test_default_arguements_that_dont_match_names_are_ignored + ta = Rake::TaskArguments.new(["aa", "bb"], [nil, "original_val"]) + ta.with_defaults({ "cc" => "default_val" }) + assert_nil ta[:cc] + end +end diff --git a/test/rake/test_task_manager.rb b/test/rake/test_task_manager.rb new file mode 100644 index 0000000000..2337946022 --- /dev/null +++ b/test/rake/test_task_manager.rb @@ -0,0 +1,169 @@ +require 'test/unit' +require 'rake' + +class TaskManager + include Rake::TaskManager +end + +class TestTaskManager < Test::Unit::TestCase + + def setup + @tm = TaskManager.new + end + + def test_create_task_manager + assert_not_nil @tm + assert_equal [], @tm.tasks + end + + def test_define_task + t = @tm.define_task(Rake::Task, :t) + assert_equal "t", t.name + assert_equal @tm, t.application + end + + def test_name_lookup + t = @tm.define_task(Rake::Task, :t) + assert_equal t, @tm[:t] + end + + def test_namespace_task_create + @tm.in_namespace("x") do + t = @tm.define_task(Rake::Task, :t) + assert_equal "x:t", t.name + end + assert_equal ["x:t"], @tm.tasks.collect { |t| t.name } + end + + def test_anonymous_namespace + anon_ns = @tm.in_namespace(nil) do + t = @tm.define_task(Rake::Task, :t) + assert_equal "_anon_1:t", t.name + end + task = anon_ns[:t] + assert_equal "_anon_1:t", task.name + end + + def test_create_filetask_in_namespace + @tm.in_namespace("x") do + t = @tm.define_task(Rake::FileTask, "fn") + assert_equal "fn", t.name + end + assert_equal ["fn"], @tm.tasks.collect { |t| t.name } + end + + def test_namespace_yields_same_namespace_as_returned + yielded_namespace = nil + returned_namespace = @tm.in_namespace("x") do |ns| + yielded_namespace = ns + end + assert_equal returned_namespace, yielded_namespace + end + + def test_name_lookup_with_implicit_file_tasks + t = @tm["README"] + assert_equal "README", t.name + assert Rake::FileTask === t + end + + def test_name_lookup_with_nonexistent_task + assert_raise(RuntimeError) { + t = @tm["DOES NOT EXIST"] + } + end + + def test_name_lookup_in_multiple_scopes + aa = nil + bb = nil + xx = @tm.define_task(Rake::Task, :xx) + top_z = @tm.define_task(Rake::Task, :z) + @tm.in_namespace("a") do + aa = @tm.define_task(Rake::Task, :aa) + mid_z = @tm.define_task(Rake::Task, :z) + @tm.in_namespace("b") do + bb = @tm.define_task(Rake::Task, :bb) + bot_z = @tm.define_task(Rake::Task, :z) + + assert_equal ["a", "b"], @tm.current_scope + + assert_equal bb, @tm["a:b:bb"] + assert_equal aa, @tm["a:aa"] + assert_equal xx, @tm["xx"] + assert_equal bot_z, @tm["z"] + assert_equal mid_z, @tm["^z"] + assert_equal top_z, @tm["^^z"] + assert_equal top_z, @tm["rake:z"] + end + + assert_equal ["a"], @tm.current_scope + + assert_equal bb, @tm["a:b:bb"] + assert_equal aa, @tm["a:aa"] + assert_equal xx, @tm["xx"] + assert_equal bb, @tm["b:bb"] + assert_equal aa, @tm["aa"] + assert_equal mid_z, @tm["z"] + assert_equal top_z, @tm["^z"] + assert_equal top_z, @tm["rake:z"] + end + + assert_equal [], @tm.current_scope + + assert_equal [], xx.scope + assert_equal ['a'], aa.scope + assert_equal ['a', 'b'], bb.scope + end + + def test_lookup_with_explicit_scopes + t1, t2, t3, s = (0...4).collect { nil } + t1 = @tm.define_task(Rake::Task, :t) + @tm.in_namespace("a") do + t2 = @tm.define_task(Rake::Task, :t) + s = @tm.define_task(Rake::Task, :s) + @tm.in_namespace("b") do + t3 = @tm.define_task(Rake::Task, :t) + end + end + assert_equal t1, @tm[:t, []] + assert_equal t2, @tm[:t, ["a"]] + assert_equal t3, @tm[:t, ["a", "b"]] + assert_equal s, @tm[:s, ["a", "b"]] + assert_equal s, @tm[:s, ["a"]] + end + + def test_correctly_scoped_prerequisites_are_invoked + values = [] + @tm = Rake::Application.new + @tm.define_task(Rake::Task, :z) do values << "top z" end + @tm.in_namespace("a") do + @tm.define_task(Rake::Task, :z) do values << "next z" end + @tm.define_task(Rake::Task, :x => :z) + end + + @tm["a:x"].invoke + assert_equal ["next z"], values + end + +end + +class TestTaskManagerArgumentResolution < Test::Unit::TestCase + def test_good_arg_patterns + assert_equal [:t, [], []], task(:t) + assert_equal [:t, [], [:x]], task(:t => :x) + assert_equal [:t, [], [:x, :y]], task(:t => [:x, :y]) + + assert_equal [:t, [:a, :b], []], task(:t, :a, :b) + assert_equal [:t, [], [:x]], task(:t, :needs => :x) + assert_equal [:t, [:a, :b], [:x]], task(:t, :a, :b, :needs => :x) + assert_equal [:t, [:a, :b], [:x, :y]], task(:t, :a, :b, :needs => [:x, :y]) + + assert_equal [:t, [:a, :b], []], task(:t, [:a, :b]) + assert_equal [:t, [:a, :b], [:x]], task(:t, [:a, :b] => :x) + assert_equal [:t, [:a, :b], [:x, :y]], task(:t, [:a, :b] => [:x, :y]) + end + + def task(*args) + tm = TaskManager.new + tm.resolve_args(args) + end +end diff --git a/test/rake/test_tasklib.rb b/test/rake/test_tasklib.rb new file mode 100644 index 0000000000..a113d80f78 --- /dev/null +++ b/test/rake/test_tasklib.rb @@ -0,0 +1,10 @@ +require 'test/unit' +require 'rake/tasklib' + + +class TestTaskLib < Test::Unit::TestCase + def test_paste + tl = Rake::TaskLib.new + assert_equal :ab, tl.paste(:a, :b) + end +end diff --git a/test/rake/test_tasks.rb b/test/rake/test_tasks.rb new file mode 100644 index 0000000000..c4948ea389 --- /dev/null +++ b/test/rake/test_tasks.rb @@ -0,0 +1,369 @@ +require 'test/unit' +require 'fileutils' +require 'rake' +require_relative 'filecreation' +require_relative 'capture_stdout' + +###################################################################### +class TestTask < Test::Unit::TestCase + include CaptureStdout + include Rake + + def setup + Task.clear + end + + def test_create + arg = nil + t = task(:name) { |task| arg = task; 1234 } + assert_equal "name", t.name + assert_equal [], t.prerequisites + assert t.needed? + t.execute(0) + assert_equal t, arg + assert_nil t.source + assert_equal [], t.sources + end + + def test_inspect + t = task(:foo, :needs => [:bar, :baz]) + assert_equal "<Rake::Task foo => [bar, baz]>", t.inspect + end + + def test_invoke + runlist = [] + t1 = task(:t1 => [:t2, :t3]) { |t| runlist << t.name; 3321 } + t2 = task(:t2) { |t| runlist << t.name } + t3 = task(:t3) { |t| runlist << t.name } + assert_equal ["t2", "t3"], t1.prerequisites + t1.invoke + assert_equal ["t2", "t3", "t1"], runlist + end + + def test_invoke_with_circular_dependencies + runlist = [] + t1 = task(:t1 => [:t2]) { |t| runlist << t.name; 3321 } + t2 = task(:t2 => [:t1]) { |t| runlist << t.name } + assert_equal ["t2"], t1.prerequisites + assert_equal ["t1"], t2.prerequisites + ex = assert_raise RuntimeError do + t1.invoke + end + assert_match(/circular dependency/i, ex.message) + assert_match(/t1 => t2 => t1/, ex.message) + end + + def test_dry_run_prevents_actions + Rake.application.options.dryrun = true + runlist = [] + t1 = task(:t1) { |t| runlist << t.name; 3321 } + out = capture_stdout { t1.invoke } + assert_match(/execute .*t1/i, out) + assert_match(/dry run/i, out) + assert_no_match(/invoke/i, out) + assert_equal [], runlist + ensure + Rake.application.options.dryrun = false + end + + def test_tasks_can_be_traced + Rake.application.options.trace = true + t1 = task(:t1) + out = capture_stdout { + t1.invoke + } + assert_match(/invoke t1/i, out) + assert_match(/execute t1/i, out) + ensure + Rake.application.options.trace = false + end + + def test_no_double_invoke + runlist = [] + t1 = task(:t1 => [:t2, :t3]) { |t| runlist << t.name; 3321 } + t2 = task(:t2 => [:t3]) { |t| runlist << t.name } + t3 = task(:t3) { |t| runlist << t.name } + t1.invoke + assert_equal ["t3", "t2", "t1"], runlist + end + + def test_can_double_invoke_with_reenable + runlist = [] + t1 = task(:t1) { |t| runlist << t.name } + t1.invoke + t1.reenable + t1.invoke + assert_equal ["t1", "t1"], runlist + end + + def test_clear + t = task("t" => "a") { } + t.clear + assert t.prerequisites.empty?, "prerequisites should be empty" + assert t.actions.empty?, "actions should be empty" + end + + def test_clear_prerequisites + t = task("t" => ["a", "b"]) + assert_equal ['a', 'b'], t.prerequisites + t.clear_prerequisites + assert_equal [], t.prerequisites + end + + def test_clear_actions + t = task("t") { } + t.clear_actions + assert t.actions.empty?, "actions should be empty" + end + + def test_find + task :tfind + assert_equal "tfind", Task[:tfind].name + ex = assert_raise(RuntimeError) { Task[:leaves] } + assert_equal "Don't know how to build task 'leaves'", ex.message + end + + def test_defined + assert ! Task.task_defined?(:a) + task :a + assert Task.task_defined?(:a) + end + + def test_multi_invocations + runs = [] + p = proc do |t| runs << t.name end + task({:t1=>[:t2,:t3]}, &p) + task({:t2=>[:t3]}, &p) + task(:t3, &p) + Task[:t1].invoke + assert_equal ["t1", "t2", "t3"], runs.sort + end + + def test_task_list + task :t2 + task :t1 => [:t2] + assert_equal ["t1", "t2"], Task.tasks.collect {|t| t.name} + end + + def test_task_gives_name_on_to_s + task :abc + assert_equal "abc", Task[:abc].to_s + end + + def test_symbols_can_be_prerequisites + task :a => :b + assert_equal ["b"], Task[:a].prerequisites + end + + def test_strings_can_be_prerequisites + task :a => "b" + assert_equal ["b"], Task[:a].prerequisites + end + + def test_arrays_can_be_prerequisites + task :a => ["b", "c"] + assert_equal ["b", "c"], Task[:a].prerequisites + end + + def test_filelists_can_be_prerequisites + task :a => FileList.new.include("b", "c") + assert_equal ["b", "c"], Task[:a].prerequisites + end + + def test_investigation_output + t1 = task(:t1 => [:t2, :t3]) { |t| runlist << t.name; 3321 } + task(:t2) + task(:t3) + out = t1.investigation + assert_match(/class:\s*Rake::Task/, out) + assert_match(/needed:\s*true/, out) + assert_match(/pre-requisites:\s*--t[23]/, out) + end + + + def test_extended_comments + desc %{ + This is a comment. + + And this is the extended comment. + name -- Name of task to execute. + rev -- Software revision to use. + } + t = task(:t, :name, :rev) + assert_equal "[name,rev]", t.arg_description + assert_equal "This is a comment.", t.comment + assert_match(/^\s*name -- Name/, t.full_comment) + assert_match(/^\s*rev -- Software/, t.full_comment) + assert_match(/\A\s*This is a comment\.$/, t.full_comment) + end + + def test_multiple_comments + desc "line one" + t = task(:t) + desc "line two" + task(:t) + assert_equal "line one / line two", t.comment + end + + def test_settable_comments + t = task(:t) + t.comment = "HI" + assert_equal "HI", t.comment + end +end + +###################################################################### +class TestTaskWithArguments < Test::Unit::TestCase + include CaptureStdout + include Rake + + def setup + Task.clear + end + + def test_no_args_given + t = task :t + assert_equal [], t.arg_names + end + + def test_args_given + t = task :t, :a, :b + assert_equal [:a, :b], t.arg_names + end + + def test_name_and_needs + t = task(:t => [:pre]) + assert_equal "t", t.name + assert_equal [], t.arg_names + assert_equal ["pre"], t.prerequisites + end + + def test_name_and_explicit_needs + t = task(:t, :needs => [:pre]) + assert_equal "t", t.name + assert_equal [], t.arg_names + assert_equal ["pre"], t.prerequisites + end + + def test_name_args_and_explicit_needs + t = task(:t, :x, :y, :needs => [:pre]) + assert_equal "t", t.name + assert_equal [:x, :y], t.arg_names + assert_equal ["pre"], t.prerequisites + end + + def test_illegal_keys_in_task_name_hash + assert_raise RuntimeError do + t = task(:t, :x, :y => 1, :needs => [:pre]) + end + end + + def test_arg_list_is_empty_if_no_args_given + t = task(:t) { |tt, args| assert_equal({}, args.to_hash) } + t.invoke(1, 2, 3) + end + + def test_tasks_can_access_arguments_as_hash + t = task :t, :a, :b, :c do |tt, args| + assert_equal({:a => 1, :b => 2, :c => 3}, args.to_hash) + assert_equal 1, args[:a] + assert_equal 2, args[:b] + assert_equal 3, args[:c] + assert_equal 1, args.a + assert_equal 2, args.b + assert_equal 3, args.c + end + t.invoke(1, 2, 3) + end + + def test_actions_of_various_arity_are_ok_with_args + notes = [] + t = task(:t, :x) do + notes << :a + end + t.enhance do | | + notes << :b + end + t.enhance do |task| + notes << :c + assert_kind_of Task, task + end + t.enhance do |t2, args| + notes << :d + assert_equal t, t2 + assert_equal({:x => 1}, args.to_hash) + end + assert_nothing_raised do t.invoke(1) end + assert_equal [:a, :b, :c, :d], notes + end + + def test_arguments_are_passed_to_block + t = task(:t, :a, :b) { |tt, args| + assert_equal( { :a => 1, :b => 2 }, args.to_hash ) + } + t.invoke(1, 2) + end + + def test_extra_parameters_are_ignored + t = task(:t, :a) { |tt, args| + assert_equal 1, args.a + assert_nil args.b + } + t.invoke(1, 2) + end + + def test_arguments_are_passed_to_all_blocks + counter = 0 + t = task :t, :a + task :t do |tt, args| + assert_equal 1, args.a + counter += 1 + end + task :t do |tt, args| + assert_equal 1, args.a + counter += 1 + end + t.invoke(1) + assert_equal 2, counter + end + + def test_block_with_no_parameters_is_ok + t = task(:t) { } + t.invoke(1, 2) + end + + def test_name_with_args + desc "T" + t = task(:tt, :a, :b) + assert_equal "tt", t.name + assert_equal "T", t.comment + assert_equal "[a,b]", t.arg_description + assert_equal "tt[a,b]", t.name_with_args + assert_equal [:a, :b],t.arg_names + end + + def test_named_args_are_passed_to_prereqs + value = nil + pre = task(:pre, :rev) { |t, args| value = args.rev } + t = task(:t, :name, :rev, :needs => [:pre]) + t.invoke("bill", "1.2") + assert_equal "1.2", value + end + + def test_args_not_passed_if_no_prereq_names + pre = task(:pre) { |t, args| + assert_equal({}, args.to_hash) + assert_equal "bill", args.name + } + t = task(:t, :name, :rev, :needs => [:pre]) + t.invoke("bill", "1.2") + end + + def test_args_not_passed_if_no_arg_names + pre = task(:pre, :rev) { |t, args| + assert_equal({}, args.to_hash) + } + t = task(:t, :needs => [:pre]) + t.invoke("bill", "1.2") + end +end diff --git a/test/rake/test_test_task.rb b/test/rake/test_test_task.rb new file mode 100644 index 0000000000..1ba04ba9bd --- /dev/null +++ b/test/rake/test_test_task.rb @@ -0,0 +1,81 @@ +require 'tmpdir' +require 'test/unit' +require 'rake/testtask' + +class TestTestTask < Test::Unit::TestCase + include Rake + + def setup + @oldwd = Dir.pwd + @tmpwd = Dir.mktmpdir + Dir.chdir(@tmpwd) + Task.clear + ENV.delete('TEST') + open('install.rb', 'w') {} + end + + def teardown + FileUtils.rm_rf("testdata") + Dir.chdir(@oldwd) + FileUtils.rm_rf(@tmpwd) + end + + def test_no_task + assert ! Task.task_defined?(:test) + end + + def test_defaults + tt = Rake::TestTask.new do |t| end + assert_not_nil tt + assert_equal :test, tt.name + assert_equal ['lib'], tt.libs + assert_equal 'test/test*.rb', tt.pattern + assert_equal false, tt.verbose + assert Task.task_defined?(:test) + end + + def test_non_defaults + tt = Rake::TestTask.new(:example) do |t| + t.libs = ['src', 'ext'] + t.pattern = 'test/tc_*.rb' + t.verbose = true + end + assert_not_nil tt + assert_equal :example, tt.name + assert_equal ['src', 'ext'], tt.libs + assert_equal 'test/tc_*.rb', tt.pattern + assert_equal true, tt.verbose + assert Task.task_defined?(:example) + end + + def test_pattern + tt = Rake::TestTask.new do |t| + t.pattern = '*.rb' + end + assert_equal ['install.rb'], tt.file_list.to_a + end + + def test_env_test + ENV['TEST'] = 'testfile.rb' + tt = Rake::TestTask.new do |t| + t.pattern = '*' + end + assert_equal ["testfile.rb"], tt.file_list.to_a + end + + def test_test_files + tt = Rake::TestTask.new do |t| + t.test_files = FileList['a.rb', 'b.rb'] + end + assert_equal ["a.rb", 'b.rb'], tt.file_list.to_a + end + + def test_both_pattern_and_test_files + tt = Rake::TestTask.new do |t| + t.test_files = FileList['a.rb', 'b.rb'] + t.pattern = '*.rb' + end + assert_equal ['a.rb', 'b.rb', 'install.rb'], tt.file_list.to_a + end + +end diff --git a/test/rake/test_top_level_functions.rb b/test/rake/test_top_level_functions.rb new file mode 100644 index 0000000000..c17fc73c4e --- /dev/null +++ b/test/rake/test_top_level_functions.rb @@ -0,0 +1,91 @@ +require 'test/unit' +require_relative 'capture_stdout' +require 'rake' + +class TestTopLevelFunctions < Test::Unit::TestCase + include CaptureStdout + + def setup + super + @app = Rake.application + Rake.application = @mock = Object.new + end + + def teardown + Rake.application = @app + super + end + + def defmock(sym, &block) + class << @mock; self; end.class_eval do + define_method(sym, block) + end + end + + def test_namespace + args = [] + defmock(:in_namespace) {|a, *| args << a} + namespace "xyz" do end + assert_equal(["xyz"], args) + end + + def test_import + args = [] + defmock(:add_import) {|a| args << a} + import('x', 'y', 'z') + assert_equal(['x', 'y', 'z'], args) + end + + def test_when_writing + out = capture_stdout do + when_writing("NOTWRITING") do + puts "WRITING" + end + end + assert_equal "WRITING\n", out + end + + def test_when_not_writing + RakeFileUtils.nowrite_flag = true + out = capture_stdout do + when_writing("NOTWRITING") do + puts "WRITING" + end + end + assert_equal "DRYRUN: NOTWRITING\n", out + ensure + RakeFileUtils.nowrite_flag = false + end + + def test_missing_constants_task + args = [] + defmock(:const_warning) {|a| args << a} + Object.const_missing(:Task) + assert_equal([:Task], args) + end + + def test_missing_constants_file_task + args = [] + defmock(:const_warning) {|a| args << a} + Object.const_missing(:FileTask) + assert_equal([:FileTask], args) + end + + def test_missing_constants_file_creation_task + args = [] + defmock(:const_warning) {|a| args << a} + Object.const_missing(:FileCreationTask) + assert_equal([:FileCreationTask], args) + end + + def test_missing_constants_rake_app + args = [] + defmock(:const_warning) {|a| args << a} + Object.const_missing(:RakeApp) + assert_equal([:RakeApp], args) + end + + def test_missing_other_constant + assert_raise(NameError) do Object.const_missing(:Xyz) end + end +end diff --git a/test/rake/test_win32.rb b/test/rake/test_win32.rb new file mode 100644 index 0000000000..a1b73de9dd --- /dev/null +++ b/test/rake/test_win32.rb @@ -0,0 +1,68 @@ +require 'test/unit' +require_relative 'in_environment' + +require 'rake' + +class TestWin32 < Test::Unit::TestCase + include InEnvironment + + Win32 = Rake::Win32 + + def test_win32_system_dir_uses_home_if_defined + in_environment('RAKE_SYSTEM' => nil, 'HOME' => 'C:\\HP') do + assert_equal "C:/HP/Rake", Win32.win32_system_dir + end + end + + def test_win32_system_dir_uses_homedrive_homepath_when_no_home_defined + in_environment( + 'RAKE_SYSTEM' => nil, + 'HOME' => nil, + 'HOMEDRIVE' => "C:", + 'HOMEPATH' => "\\HP" + ) do + assert_equal "C:/HP/Rake", Win32.win32_system_dir + end + end + + def test_win32_system_dir_uses_appdata_when_no_home_or_home_combo + in_environment( + 'RAKE_SYSTEM' => nil, + 'HOME' => nil, + 'HOMEDRIVE' => nil, + 'HOMEPATH' => nil, + 'APPDATA' => "C:\\Documents and Settings\\HP\\Application Data" + ) do + assert_equal "C:/Documents and Settings/HP/Application Data/Rake", Win32.win32_system_dir + end + end + + def test_win32_system_dir_fallback_to_userprofile_otherwise + in_environment( + 'RAKE_SYSTEM' => nil, + 'HOME' => nil, + 'HOMEDRIVE' => nil, + 'HOMEPATH' => nil, + 'APPDATA' => nil, + 'USERPROFILE' => "C:\\Documents and Settings\\HP" + ) do + assert_equal "C:/Documents and Settings/HP/Rake", Win32.win32_system_dir + end + end + + def test_win32_system_dir_nil_of_no_env_vars + in_environment( + 'RAKE_SYSTEM' => nil, + 'HOME' => nil, + 'HOMEDRIVE' => nil, + "HOMEPATH" => nil, + 'APPDATA' => nil, + "USERPROFILE" => nil + ) do + assert_raise(Rake::Win32::Win32HomeError) do + Win32.win32_system_dir + end + end + end + +end if Rake::Win32.windows? |