######################################################################
# tc_find.rb
#
# Test case for the File::Find package. You should run this via the
# 'rake test' task.
######################################################################
require 'test/unit'
require 'fileutils'
require 'file/find'

class TC_File_Find < Test::Unit::TestCase
   WINDOWS = RUBY_PLATFORM.match('mswin') ? true : false

   def setup
      @file1 = 'test1.rb'
      @file2 = 'test1.txt'
      @file3 = 'foo.txt'
      @dir1  = 'dir1'
      @dir2  = 'dir2'

      File.open(@file1, 'w'){}
      File.open(@file2, 'w'){}
      File.open(@file3, 'w'){}

      unless WINDOWS
         @link1 = 'link1'
         File.symlink(@file1, @link1)
      end

      Dir.mkdir(@dir1) unless File.exists?(@dir1)
      Dir.mkdir(@dir2) unless File.exists?(@dir2)

      File.open(File.join(@dir1, 'bar.txt'), 'w'){}
      File.open(File.join(@dir2, 'baz.txt'), 'w'){}

      @rule1 = File::Find.new(:name => '*.rb')
   end

   def test_version
      assert_equal('0.2.1', File::Find::VERSION)
   end

   def test_path
      assert_respond_to(@rule1, :path)
      assert_respond_to(@rule1, :path=)
      assert_equal(Dir.pwd, @rule1.path)
   end

   def test_options
      assert_respond_to(@rule1, :options)
      assert_respond_to(@rule1, :options=)
      assert_equal({:name => '*.rb'}, @rule1.options)
   end

   def test_atime_basic
      assert_respond_to(@rule1, :atime)
      assert_respond_to(@rule1, :atime=)
      assert_nil(@rule1.atime)
   end

   def test_atime
      rule1 = File::Find.new(:name => "*.rb", :atime => 0)
      rule2 = File::Find.new(:name => "*.rb", :atime => 1)

      assert_equal(false, rule1.find.empty?)
      assert_equal(true, rule2.find.empty?)
   end

   def test_ctime_basic
      assert_respond_to(@rule1, :ctime)
      assert_respond_to(@rule1, :ctime=)
      assert_nil(@rule1.ctime)
   end

   def test_ctime
      rule1 = File::Find.new(:name => "*.rb", :ctime => 0)
      rule2 = File::Find.new(:name => "*.rb", :ctime => 1)

      assert_equal(false, rule1.find.empty?)
      assert_equal(true, rule2.find.empty?)
   end

   def test_ftype_basic
      assert_respond_to(@rule1, :ftype)
      assert_respond_to(@rule1, :ftype=)
      assert_nil(@rule1.ftype)
   end

   def test_ftype
      rule1 = File::Find.new(:name => "*.rb", :ftype => "file")
      rule2 = File::Find.new(:name => "*.rb", :ftype => "characterSpecial")

      assert_equal(false, rule1.find.empty?)
      assert_equal(true, rule2.find.empty?)
   end

   def test_group_basic
      assert_respond_to(@rule1, :group)
      assert_respond_to(@rule1, :group=)
      assert_nil(@rule1.group)
   end

   def test_inum_basic
      assert_respond_to(@rule1, :inum)
      assert_respond_to(@rule1, :inum=)
      assert_nil(@rule1.inum)
   end

   def test_follow_basic
      assert_respond_to(@rule1, :follow)
      assert_respond_to(@rule1, :follow=)
      assert_equal(true, @rule1.follow)
   end

   def test_name_basic
      assert_respond_to(@rule1, :name)
      assert_respond_to(@rule1, :name=)
      assert_equal('*.rb', @rule1.name)
   end

   def test_pattern_alias
      assert_respond_to(@rule1, :pattern)
      assert_respond_to(@rule1, :pattern=)
      assert_equal('*.rb', @rule1.pattern)
   end

   def test_perm_basic
      assert_respond_to(@rule1, :perm)
      assert_respond_to(@rule1, :perm=)
      assert_nil(@rule1.perm)
   end

   # Skip on MS Windows for now
   unless WINDOWS
      def test_perm
         File.chmod(0664, @file1) 
         File.chmod(0644, @file2) 
         results = File::Find.new(:name => "test1*", :perm => 664).find

         assert_equal(1, results.length)
         assert_equal('test1.rb', File.basename(results.first))
      end
   end

   def test_prune_basic
      assert_respond_to(@rule1, :prune)
      assert_respond_to(@rule1, :prune=)
      assert_nil(@rule1.prune)
   end

   def test_prune
      rule = File::Find.new(:name => "*.txt", :prune => 'foo')
      assert_equal('test1.txt', File.basename(rule.find.first))
   end

   def test_size_basic
      assert_respond_to(@rule1, :size)
      assert_respond_to(@rule1, :size=)
      assert_nil(@rule1.size)
   end

   def test_user_basic
      assert_respond_to(@rule1, :user)
      assert_respond_to(@rule1, :user=)
      assert_nil(@rule1.user)
   end

   def test_previous_basic
      assert_respond_to(@rule1, :previous)
   end

   def test_expected_errors
      assert_raises(Errno::ENOENT){ File::Find.new(:path => '/bogus/dir').find }
   end

   def teardown
      FileUtils.rm_rf(@file1)
      FileUtils.rm_rf(@file2)
      FileUtils.rm_rf(@file3)
      FileUtils.rm_rf(@dir1)
      FileUtils.rm_rf(@dir2)
      FileUtils.rm_rf(@link1) unless WINDOWS
   end
end