pathname2-1.8.0/0000755000004100000410000000000012734555701013440 5ustar www-datawww-datapathname2-1.8.0/Rakefile0000644000004100000410000001306212734555701015107 0ustar www-datawww-datarequire 'rake' require 'rake/clean' require 'rake/testtask' CLEAN.include("**/*.gem", "**/*.rbc") namespace :gem do desc "Build the pathname2 gem" task :create => [:clean] do require 'rubygems/package' spec = eval(IO.read('pathname2.gemspec')) spec.signing_key = File.join(Dir.home, '.ssh', 'gem-private_key.pem') Gem::Package.build(spec, true) end desc "Install the pathname2 gem" task :install => [:create] do file = Dir["*.gem"].first sh "gem install -l #{file}" end end desc 'Run the test suite for the pure Ruby version' Rake::TestTask.new('test') do |t| t.warning = true t.verbose = true if File::ALT_SEPARATOR t.test_files = FileList["test/windows/*.rb"] + FileList["test/test_version.rb"] else t.test_files = FileList['test/test_pathname.rb'] end end namespace :test do dir = File::ALT_SEPARATOR ? "windows" : "unix" Rake::TestTask.new(:all) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/*.rb"] + FileList["test/test_version.rb"] end Rake::TestTask.new(:append) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_append.rb"] end Rake::TestTask.new(:aref) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_aref.rb"] end Rake::TestTask.new(:ascend) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_ascend.rb"] end Rake::TestTask.new(:children) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_children.rb"] end Rake::TestTask.new(:clean) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_clean.rb"] end Rake::TestTask.new(:clean!) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_clean_bang.rb"] end Rake::TestTask.new(:constructor) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_constructor.rb"] end Rake::TestTask.new(:descend) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_descend.rb"] end Rake::TestTask.new(:drive_number) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_drive_number.rb"] end Rake::TestTask.new(:each) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_each.rb"] end Rake::TestTask.new(:facade) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_facade.rb"] end Rake::TestTask.new(:is_absolute) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_is_absolute.rb"] end Rake::TestTask.new(:is_relative) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_is_relative.rb"] end Rake::TestTask.new(:is_root) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_is_root.rb"] end Rake::TestTask.new(:is_unc) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_is_unc.rb"] end Rake::TestTask.new(:join) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_join.rb"] end Rake::TestTask.new(:long_path) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_long_path.rb"] end Rake::TestTask.new(:misc) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_misc.rb"] end Rake::TestTask.new(:parent) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_parent.rb"] end Rake::TestTask.new(:pstrip) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_pstrip.rb"] end Rake::TestTask.new(:pstrip!) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_pstrip_bang.rb"] end Rake::TestTask.new(:realpath) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_realpath.rb"] end Rake::TestTask.new(:relative_path_from) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_relative_path_from.rb"] end Rake::TestTask.new(:root) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_root.rb"] end Rake::TestTask.new(:short_path) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_short_path.rb"] end Rake::TestTask.new(:to_a) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_to_a.rb"] end Rake::TestTask.new(:undecorate) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_undecorate.rb"] end Rake::TestTask.new(:undecorate!) do |t| t.warning = true t.verbose = true t.test_files = FileList["test/#{dir}/test_undecorate_bang.rb"] end end desc 'Run the Pathname benchmark suite' task :benchmark do sh 'ruby -Ilib benchmarks/bench_pathname.rb' end desc 'Run the benchmark suite for Pathname#+ vs File.join' task :benchmark_plus do sh 'ruby -Ilib benchmarks/bench_plus.rb' end task :default => :test pathname2-1.8.0/examples/0000755000004100000410000000000012734555701015256 5ustar www-datawww-datapathname2-1.8.0/examples/example_pathname.rb0000644000004100000410000000132012734555701021107 0ustar www-datawww-data######################################################################## # example_pathname.rb # # Some examples to demonstrate the behavior of the pathname2 library. ######################################################################## require 'pathname2' puts "VERSION: " + Pathname::VERSION path1 = Pathname.new("foo/bar") path2 = Pathname.new("baz/blah") path3 = Pathname.new("foo/../bar") path4 = Pathname.new("../baz") p path1 + path2 # foo/bar/baz/blah p path3 + path4 # baz # Shortcut syntax path = pn{ "C:\\Documents and Settings\\snoopy\\My Documents" } p path[0] # C: p path[1] # Documents and Settings p path[0,2] # C:\\Documents and Settings p path[0..2] # C:\\Documents and Settings\\snoopypathname2-1.8.0/README0000644000004100000410000000610312734555701014320 0ustar www-datawww-data== Description A drop-in replacement for the current Pathname class. == Prerequisites * facade * ffi (Windows only) * test-unit (testing only) == Installation gem install pathname2 == Synopsis require 'pathname2' # Unix path1 = Pathname.new("/foo/bar/baz") path2 = Pathname.new("../zap") path1 + path2 # "/foo/bar/zap" path1 / path2 # "/foo/bar/zap" (same as +) path1.exists? # Does this path exist? path1.dirname # "/foo/bar" path1.to_a # ['foo','bar','baz'] # Windows path1 = Pathname.new("C:/foo/bar/baz") path2 = Pathname.new("../zap") path1 + path2 # "C:\\foo\\bar\\zap" path1.root # "C:\\" path1.to_a # ['C:','foo','bar','baz'] == Windows Notes All forward slashes are converted to backslashes for Pathname objects. == Differences between Unix and Windows If your pathname consists solely of ".", or "..", the return value for Pathname#clean will be different. On Win32, "\\" is returned, while on Unix "." is returned. I consider this an extreme edge case and will not worry myself with it. == Differences between Pathname in the standard library and this version * It is a subclass of String (and thus, mixes in Enumerable). * It has sensical to_a and root instance methods. * It works on Windows and Unix. The current implementation does not work with Windows path names very well, and not at all when it comes to UNC paths. * The Pathname#cleanpath method works differently - it always returns a canonical pathname. In addition, there is no special consideration for symlinks (yet), though I'm not sure it warrants it. * The Pathname#+ method auto cleans. * It uses a facade for all File and Dir methods, as well as most FileUtils methods. * Pathname#clean works slightly differently. In the stdlib version, Pathname#clean("../a") returns "../a". In this version, it returns "a". This affects other methods, such as Pathname#relative_path_from. * Accepts file urls and converts them to paths automatically, e.g. file:///foo%20bar/baz becomes '/foo/bar/baz'. * Adds a Kernel level +pn+ method as a shortcut. * Allows you to add paths together with the '/' operator. == Method Priority Because there is some overlap in method names between File, Dir, and FileUtils, the priority is as follows: * File * Dir * FileUtils In other words, whichever of these defines a given method first is the method that is used by the pathname2 library. == Known Issues On MS Windows, some methods may not work on pathnames greater than 260 characters because of internal function limitations. Any issues you find should be reported on the project page at https://github.com/djberg96/pathname2 == Future Plans Suggestions welcome. == License Apache 2.0 == Copyright (C) 2003-2016 Daniel J. Berger All rights reserved. == Warranty This library is provided "as is" and without any express or implied warranties, including, without limitation, the implied warranties of merchantability and fitness for a particular purpose. == Author Daniel J. Berger pathname2-1.8.0/data.tar.gz.sig0000444000004100000410000000040012734555701016251 0ustar www-datawww-datam=\Kn @ӵݛ`h5ps>c;!ܴI'l>;*LBRjAy^78cs=從kY`4 ȱ7G΂ 4Lum2%L&jonX"z}8AYۀ zD=߹󧵕ÒnCD6 )uА,a Tq3hn7ͨFـYJnv_6:j3dI pathname2-1.8.0/lib/0000755000004100000410000000000012734555701014206 5ustar www-datawww-datapathname2-1.8.0/lib/pathname2.rb0000644000004100000410000006432012734555701016417 0ustar www-datawww-data# == Synopsis # # Pathname represents a path name on a filesystem. A Pathname can be # relative or absolute. It does not matter whether the path exists or not. # # All functionality from File, FileTest, and Dir is included, using a facade # pattern. # # This class works on both Unix and Windows, including UNC path names. Note # that forward slashes are converted to backslashes on Windows systems. # # == Usage # # require "pathname2" # # # Unix # path1 = Pathname.new("/foo/bar/baz") # path2 = Pathname.new("../zap") # # path1 + path2 # "/foo/bar/zap" # path1.dirname # "/foo/bar" # # # Windows # path1 = Pathname.new("C:\\foo\\bar\\baz") # path2 = Pathname.new("..\\zap") # # path1 + path2 # "C:\\foo\\bar\\zap" # path1.exists? # Does the path exist? # require 'facade' require 'fileutils' require 'pp' if File::ALT_SEPARATOR require 'ffi' class String # Convenience method for converting strings to UTF-16LE for wide character # functions that require it. def wincode if self.encoding.name != 'UTF-16LE' temp = self.dup (temp.tr(File::SEPARATOR, File::ALT_SEPARATOR) << 0.chr).encode('UTF-16LE') end end end end # You're mine now. Object.send(:remove_const, :Pathname) if defined?(Pathname) class Pathname < String class Error < StandardError; end extend Facade undef_method :pretty_print facade File, File.methods(false).map{ |m| m.to_sym } - [ :chmod, :lchmod, :chown, :lchown, :dirname, :fnmatch, :fnmatch?, :link, :open, :realpath, :rename, :symlink, :truncate, :utime, :basename, :expand_path, :join ] facade Dir, Dir.methods(false).map{ |m| m.to_sym } - [ :chdir, :entries, :glob, :foreach, :mkdir, :open ] private alias :_plus_ :+ # Used to prevent infinite loops in some cases if File::ALT_SEPARATOR extend FFI::Library ffi_lib :shlwapi attach_function :PathAppendW, [:pointer, :pointer], :bool attach_function :PathCanonicalizeW, [:pointer, :buffer_in], :bool attach_function :PathCreateFromUrlW, [:buffer_in, :pointer, :pointer, :ulong], :long attach_function :PathGetDriveNumberW, [:buffer_in], :int attach_function :PathIsRelativeW, [:buffer_in], :bool attach_function :PathIsRootW, [:buffer_in], :bool attach_function :PathIsUNCW, [:buffer_in], :bool attach_function :PathIsURLW, [:buffer_in], :bool attach_function :PathRemoveBackslashW, [:buffer_in], :pointer attach_function :PathStripToRootW, [:pointer], :bool attach_function :PathUndecorateW, [:pointer], :void ffi_lib :kernel32 attach_function :GetLongPathNameW, [:buffer_in, :buffer_out, :ulong], :ulong attach_function :GetShortPathNameW, [:buffer_in, :pointer, :ulong], :ulong end public # The version of the pathname2 library VERSION = '1.8.0' # The maximum length of a path MAXPATH = 1024 unless defined? MAXPATH # Yes, I willfully violate POSIX # Returns the expanded path of the current working directory. # # Synonym for Pathname.new(Dir.pwd). # def self.pwd new(Dir.pwd) end class << self alias getwd pwd end # Creates and returns a new Pathname object. # # On platforms that define File::ALT_SEPARATOR, all forward slashes are # replaced with the value of File::ALT_SEPARATOR. On MS Windows, for # example, all forward slashes are replaced with backslashes. # # File URL's will be converted to Pathname objects, e.g. the file URL # "file:///C:/Documents%20and%20Settings" will become 'C:\Documents and Settings'. # # Examples: # # Pathname.new("/foo/bar/baz") # Pathname.new("foo") # Pathname.new("file:///foo/bar/baz") # Pathname.new("C:\\Documents and Settings\\snoopy") # def initialize(path) if path.length > MAXPATH msg = "string too long. maximum string length is " + MAXPATH.to_s raise ArgumentError, msg end @sep = File::ALT_SEPARATOR || File::SEPARATOR @win = File::ALT_SEPARATOR # Handle File URL's. The separate approach for Windows is necessary # because Ruby's URI class does not (currently) parse absolute file URL's # properly when they include a drive letter. if @win wpath = path.wincode if PathIsURLW(wpath) buf = FFI::MemoryPointer.new(:char, MAXPATH) len = FFI::MemoryPointer.new(:ulong) len.write_ulong(buf.size) if PathCreateFromUrlW(wpath, buf, len, 0) == 0 path = buf.read_string(path.size * 2).tr(0.chr, '') else raise Error, "invalid file url: #{path}" end end else if path.index('file:///', 0) require 'uri' path = URI::Parser.new.unescape(path)[7..-1] end end # Convert forward slashes to backslashes on Windows path = path.tr(File::SEPARATOR, File::ALT_SEPARATOR) if @win super(path) end # Returns a real (absolute) pathname of +self+ in the actual filesystem. # # Unlike most Pathname methods, this one assumes that the path actually # exists on your filesystem. If it doesn't, an error is raised. If a # circular symlink is encountered a system error will be raised. # # Example: # # Dir.pwd # => /usr/local # File.exists?('foo') # => true # Pathname.new('foo').realpath # => /usr/local/foo # def realpath File.stat(self) # Check to ensure that the path exists if File.symlink?(self) file = self.dup while true file = File.join(File.dirname(file), File.readlink(file)) break unless File.symlink?(file) end self.class.new(file).clean else self.class.new(Dir.pwd) + self end end # Returns the children of the directory, files and subdirectories, as an # array of Pathname objects. If you set +with_directory+ to +false+, then # the returned pathnames will contain the filename only. # # Note that the result never contain the entries '.' and '..' in the # the directory because they are not children. Also note that this method # is *not* recursive. # # Example: # # path = Pathname.new('/usr/bin') # path.children # => ['/usr/bin/ruby', '/usr/bin/perl', ...] # path.children(false) # => ['ruby', 'perl', ...] # def children(with_directory = true) with_directory = false if self == '.' result = [] Dir.foreach(self) { |file| next if file == '.' || file == '..' if with_directory result << self.class.new(File.join(self, file)) else result << self.class.new(file) end } result end # Windows only # # Removes the decoration from a path string. Non-destructive. # # Example: # # path = Pathname.new('C:\Path\File[5].txt') # path.undecorate # => C:\Path\File.txt. # def undecorate unless @win raise NotImplementedError, "not supported on this platform" end wpath = FFI::MemoryPointer.from_string(self.wincode) PathUndecorateW(wpath) self.class.new(wpath.read_string(wpath.size).split("\000\000").first.tr(0.chr, '')) end # Windows only # # Performs the substitution of Pathname#undecorate in place. # def undecorate! self.replace(undecorate) end # Windows only # # Returns the short path for a long path name. # # Example: # # path = Pathname.new('C:\Program Files\Java') # path.short_path # => C:\Progra~1\Java. # def short_path raise NotImplementedError, "not supported on this platform" unless @win buf = FFI::MemoryPointer.new(:char, MAXPATH) wpath = self.wincode size = GetShortPathNameW(wpath, buf, buf.size) raise SystemCallError.new('GetShortPathName', FFI.errno) if size == 0 self.class.new(buf.read_bytes(size * 2).delete(0.chr)) end # Windows only # # Returns the long path for a long path name. # # Example: # # path = Pathname.new('C:\Progra~1\Java') # path.long_path # => C:\Program Files\Java. # def long_path raise NotImplementedError, "not supported on this platform" unless @win buf = FFI::MemoryPointer.new(:char, MAXPATH) wpath = self.wincode size = GetLongPathNameW(wpath, buf, buf.size) raise SystemCallError.new('GetShortPathName', FFI.errno) if size == 0 self.class.new(buf.read_bytes(size * 2).delete(0.chr)) end # Removes all trailing slashes, if present. Non-destructive. # # Example: # # path = Pathname.new('/usr/local/') # path.pstrip # => '/usr/local' # def pstrip str = self.dup return str if str.empty? while ["/", "\\"].include?(str.to_s[-1].chr) str.strip! str.chop! end self.class.new(str) end # Performs the substitution of Pathname#pstrip in place. # def pstrip! self.replace(pstrip) end # Splits a pathname into strings based on the path separator. # # Examples: # # Pathname.new('/usr/local/bin').to_a # => ['usr', 'local', 'bin'] # Pathname.new('C:\WINNT\Fonts').to_a # => ['C:', 'WINNT', 'Fonts'] # def to_a # Split string by path separator if @win array = tr(File::SEPARATOR, File::ALT_SEPARATOR).split(@sep) else array = split(@sep) end array.delete("") # Remove empty elements array end # Yields each component of the path name to a block. # # Example: # # Pathname.new('/usr/local/bin').each{ |element| # puts "Element: #{element}" # } # # Yields 'usr', 'local', and 'bin', in turn # def each to_a.each{ |element| yield element } end # Returns the path component at +index+, up to +length+ components, joined # by the path separator. If the +index+ is a Range, then that is used # instead and the +length+ is ignored. # # Keep in mind that on MS Windows the drive letter is the first element. # # Examples: # # path = Pathname.new('/home/john/source/ruby') # path[0] # => 'home' # path[1] # => 'john' # path[0, 3] # => '/home/john/source' # path[0..1] # => '/home/john' # # path = Pathname.new('C:/Documents and Settings/John/Source/Ruby') # path[0] # => 'C:\' # path[1] # => 'Documents and Settings' # path[0, 3] # => 'C:\Documents and Settings\John' # path[0..1] # => 'C:\Documents and Settings' # def [](index, length=nil) if index.is_a?(Fixnum) if length path = File.join(to_a[index, length]) else path = to_a[index] end elsif index.is_a?(Range) if length warn 'Length argument ignored' end path = File.join(to_a[index]) else raise TypeError, "Only Fixnums and Ranges allowed as first argument" end if path && @win path = path.tr("/", "\\") end path end # Yields each component of the path, concatenating the next component on # each iteration as a new Pathname object, starting with the root path. # # Example: # # path = Pathname.new('/usr/local/bin') # # path.descend{ |name| # puts name # } # # First iteration => '/' # Second iteration => '/usr' # Third iteration => '/usr/local' # Fourth iteration => '/usr/local/bin' # def descend if root? yield root return end if @win path = unc? ? "#{root}\\" : "" else path = absolute? ? root : "" end # Yield the root directory if an absolute path (and not Windows) unless @win && !unc? yield root if absolute? end each{ |element| if @win && unc? next if root.to_a.include?(element) end path << element << @sep yield self.class.new(path.chop) } end # Yields the path, minus one component on each iteration, as a new # Pathname object, ending with the root path. # # Example: # # path = Pathname.new('/usr/local/bin') # # path.ascend{ |name| # puts name # } # # First iteration => '/usr/local/bin' # Second iteration => '/usr/local' # Third iteration => '/usr' # Fourth iteration => '/' # def ascend if root? yield root return end n = to_a.length while n > 0 path = to_a[0..n-1].join(@sep) if absolute? if @win && unc? path = "\\\\" << path end unless @win path = root << path end end path = self.class.new(path) yield path if @win && unc? break if path.root? end n -= 1 end # Yield the root directory if an absolute path (and not Windows) unless @win yield root if absolute? end end # Returns the root directory of the path, or '.' if there is no root # directory. # # On Unix, this means the '/' character. On Windows, this can refer # to the drive letter, or the server and share path if the path is a # UNC path. # # Examples: # # Pathname.new('/usr/local').root # => '/' # Pathname.new('lib').root # => '.' # # On MS Windows: # # Pathname.new('C:\WINNT').root # => 'C:' # Pathname.new('\\some\share\foo').root # => '\\some\share' # def root dir = "." if @win wpath = FFI::MemoryPointer.from_string(self.wincode) if PathStripToRootW(wpath) dir = wpath.read_string(wpath.size).split("\000\000").first.tr(0.chr, '') end else dir = "/" if self =~ /^\// end self.class.new(dir) end # Returns whether or not the path consists only of a root directory. # # Examples: # # Pathname.new('/').root? # => true # Pathname.new('/foo').root? # => false # def root? if @win PathIsRootW(self.wincode) else self == root end end # MS Windows only # # Determines if the string is a valid Universal Naming Convention (UNC) # for a server and share path. # # Examples: # # Pathname.new("\\\\foo\\bar").unc? # => true # Pathname.new('C:\Program Files').unc? # => false # def unc? raise NotImplementedError, "not supported on this platform" unless @win PathIsUNCW(self.wincode) end # MS Windows only # # Returns the drive number that corresponds to the root, or nil if not # applicable. # # Example: # # Pathname.new("C:\\foo").drive_number # => 2 # def drive_number unless @win raise NotImplementedError, "not supported on this platform" end num = PathGetDriveNumberW(self.wincode) num >= 0 ? num : nil end # Compares two Pathname objects. Note that Pathnames may only be compared # against other Pathnames, not strings. Otherwise nil is returned. # # Example: # # path1 = Pathname.new('/usr/local') # path2 = Pathname.new('/usr/local') # path3 = Pathname.new('/usr/local/bin') # # path1 <=> path2 # => 0 # path1 <=> path3 # => -1 # def <=>(string) return nil unless string.kind_of?(Pathname) super end # Returns the parent directory of the given path. # # Example: # # Pathname.new('/usr/local/bin').parent # => '/usr/local' # def parent return self if root? self + ".." # Use our custom '+' method end # Returns a relative path from the argument to the receiver. If +self+ # is absolute, the argument must be absolute too. If +self+ is relative, # the argument must be relative too. For relative paths, this method uses # an imaginary, common parent path. # # This method does not access the filesystem. It assumes no symlinks. # You should only compare directories against directories, or files against # files, or you may get unexpected results. # # Raises an ArgumentError if it cannot find a relative path. # # Examples: # # path = Pathname.new('/usr/local/bin') # path.relative_path_from('/usr/bin') # => "../local/bin" # # path = Pathname.new("C:\\WINNT\\Fonts") # path.relative_path_from("C:\\Program Files") # => "..\\WINNT\\Fonts" # def relative_path_from(base) base = self.class.new(base) unless base.kind_of?(Pathname) if self.absolute? != base.absolute? raise ArgumentError, "relative path between absolute and relative path" end return self.class.new(".") if self == base return self if base == "." # Because of the way the Windows version handles Pathname#clean, we need # a little extra help here. if @win if root != base.root msg = 'cannot determine relative paths from different root paths' raise ArgumentError, msg end if base == '..' && (self != '..' || self != '.') raise ArgumentError, "base directory may not contain '..'" end end dest_arr = self.clean.to_a base_arr = base.clean.to_a dest_arr.delete('.') base_arr.delete('.') # diff_arr = dest_arr - base_arr while !base_arr.empty? && !dest_arr.empty? && base_arr[0] == dest_arr[0] base_arr.shift dest_arr.shift end if base_arr.include?("..") raise ArgumentError, "base directory may not contain '..'" end base_arr.fill("..") rel_path = base_arr + dest_arr if rel_path.empty? self.class.new(".") else self.class.new(rel_path.join(@sep)) end end # Adds two Pathname objects together, or a Pathname and a String. It # also automatically cleans the Pathname. # # Adding a root path to an existing path merely replaces the current # path. Adding '.' to an existing path does nothing. # # Example: # # path1 = '/foo/bar' # path2 = '../baz' # path1 + path2 # '/foo/baz' # def +(string) unless string.kind_of?(Pathname) string = self.class.new(string) end # Any path plus "." is the same directory return self if string == "." return string if self == "." # Use the builtin PathAppend() function if on Windows - much easier if @win path = FFI::MemoryPointer.new(:char, MAXPATH) path.write_string(self.dup.wincode) more = FFI::MemoryPointer.from_string(string.wincode) PathAppendW(path, more) path = path.read_string(path.size).split("\000\000").first.delete(0.chr) return self.class.new(path) # PathAppend cleans automatically end # If the string is an absolute directory, return it return string if string.absolute? array = to_a + string.to_a new_string = array.join(@sep) unless relative? || @win temp = @sep + new_string # Add root path back if needed new_string.replace(temp) end self.class.new(new_string).clean end alias :/ :+ # Returns whether or not the path is an absolute path. # # Example: # # Pathname.new('/usr/bin').absolute? # => true # Pathname.new('usr').absolute? # => false # def absolute? !relative? end # Returns whether or not the path is a relative path. # # Example: # # Pathname.new('/usr/bin').relative? # => true # Pathname.new('usr').relative? # => false # def relative? if @win PathIsRelativeW(self.wincode) else root == "." end end # Removes unnecessary '.' paths and ellides '..' paths appropriately. # This method is non-destructive. # # Example: # # path = Pathname.new('/usr/./local/../bin') # path.clean # => '/usr/bin' # def clean return self if self.empty? if @win ptr = FFI::MemoryPointer.new(:char, MAXPATH) if PathCanonicalizeW(ptr, self.wincode) return self.class.new(ptr.read_string(ptr.size).delete(0.chr)) else return self end end final = [] to_a.each{ |element| next if element == "." final.push(element) if element == ".." && self != ".." 2.times{ final.pop } end } final = final.join(@sep) final = root._plus_(final) if root != "." final = "." if final.empty? self.class.new(final) end alias :cleanpath :clean # Identical to Pathname#clean, except that it modifies the receiver # in place. # def clean! self.replace(clean) end alias cleanpath! clean! # Similar to File.dirname, but this method allows you to specify the number # of levels up you wish to refer to. # # The default level is 1, i.e. it works the same as File.dirname. A level of # 0 will return the original path. A level equal to or greater than the # number of path elements will return the root path. # # A number less than 0 will raise an ArgumentError. # # Example: # # path = Pathname.new('/usr/local/bin/ruby') # # puts path.dirname # => /usr/local/bin # puts path.dirname(2) # => /usr/local # puts path.dirname(3) # => /usr # puts path.dirname(9) # => / # def dirname(level = 1) raise ArgumentError if level < 0 local_path = self.dup level.times{ |n| local_path = File.dirname(local_path) } self.class.new(local_path) end # Joins the given pathnames onto +self+ to create a new Pathname object. # # path = Pathname.new("C:/Users") # path = path.join("foo", "Downloads") # => C:/Users/foo/Downloads # def join(*args) args.unshift self result = args.pop result = self.class.new(result) unless result === self.class return result if result.absolute? args.reverse_each{ |path| path = self.class.new(path) unless path === self.class result = path + result break if result.absolute? } result end # A custom pretty printer def pretty_print(q) if File::ALT_SEPARATOR q.text(self.to_s.tr(File::SEPARATOR, File::ALT_SEPARATOR)) else q.text(self.to_s) end end #-- Find facade # Pathname#find is an iterator to traverse a directory tree in a depth first # manner. It yields a Pathname for each file under the directory passed to # Pathname.new. # # Since it is implemented by the Find module, Find.prune can be used to # control the traverse. # # If +self+ is ".", yielded pathnames begin with a filename in the current # current directory, not ".". # def find(&block) require "find" if self == "." Find.find(self){ |f| yield self.class.new(f.sub(%r{\A\./}, '')) } else Find.find(self){ |f| yield self.class.new(f) } end end #-- IO methods not handled by facade # IO.foreach def foreach(*args, &block) IO.foreach(self, *args, &block) end # IO.read def read(*args) IO.read(self, *args) end # IO.readlines def readlines(*args) IO.readlines(self, *args) end # IO.sysopen def sysopen(*args) IO.sysopen(self, *args) end #-- Dir methods not handled by facade # Dir.glob # # :no-doc: # This differs from Tanaka's implementation in that it does a temporary # chdir to the path in question, then performs the glob. # def glob(*args) Dir.chdir(self){ if block_given? Dir.glob(*args){ |file| yield self.class.new(file) } else Dir.glob(*args).map{ |file| self.class.new(file) } end } end # Dir.chdir def chdir(&block) Dir.chdir(self, &block) end # Dir.entries def entries Dir.entries(self).map{ |file| self.class.new(file) } end # Dir.mkdir def mkdir(*args) Dir.mkdir(self, *args) end # Dir.opendir def opendir(&block) Dir.open(self, &block) end #-- File methods not handled by facade # File.chmod def chmod(mode) File.chmod(mode, self) end # File.lchmod def lchmod(mode) File.lchmod(mode, self) end # File.chown def chown(owner, group) File.chown(owner, group, self) end # File.lchown def lchown(owner, group) File.lchown(owner, group, self) end # File.fnmatch def fnmatch(pattern, *args) File.fnmatch(pattern, self, *args) end # File.fnmatch? def fnmatch?(pattern, *args) File.fnmatch?(pattern, self, *args) end # File.link def link(old) File.link(old, self) end # File.open def open(*args, &block) File.open(self, *args, &block) end # File.rename def rename(name) File.rename(self, name) end # File.symlink def symlink(old) File.symlink(old, self) end # File.truncate def truncate(length) File.truncate(self, length) end # File.utime def utime(atime, mtime) File.utime(atime, mtime, self) end # File.basename def basename(*args) self.class.new(File.basename(self, *args)) end # File.expand_path def expand_path(*args) self.class.new(File.expand_path(self, *args)) end #-- # FileUtils facade. Note that methods already covered by File and Dir # are not defined here (pwd, mkdir, etc). #++ # FileUtils.cd def cd(*args, &block) FileUtils.cd(self, *args, &block) end # FileUtils.mkdir_p def mkdir_p(*args) FileUtils.mkdir_p(self, *args) end alias mkpath mkdir_p # FileUtils.ln def ln(*args) FileUtils.ln(self, *args) end # FileUtils.ln_s def ln_s(*args) FileUtils.ln_s(self, *args) end # FileUtils.ln_sf def ln_sf(*args) FileUtils.ln_sf(self, *args) end # FileUtils.cp def cp(*args) FileUtils.cp(self, *args) end # FileUtils.cp_r def cp_r(*args) FileUtils.cp_r(self, *args) end # FileUtils.mv def mv(*args) FileUtils.mv(self, *args) end # FileUtils.rm def rm(*args) FileUtils.rm(self, *args) end alias remove rm # FileUtils.rm_f def rm_f(*args) FileUtils.rm_f(self, *args) end # FileUtils.rm_r def rm_r(*args) FileUtils.rm_r(self, *args) end # FileUtils.rm_rf def rm_rf(*args) FileUtils.rm_rf(self, *args) end # FileUtils.rmtree def rmtree(*args) FileUtils.rmtree(self, *args) end # FileUtils.install def install(*args) FileUtils.install(self, *args) end # FileUtils.touch def touch(*args) FileUtils.touch(*args) end # FileUtils.compare_file def compare_file(file) FileUtils.compare_file(self, file) end # FileUtils.uptodate? def uptodate?(*args) FileUtils.uptodate(self, *args) end # FileUtils.copy_file def copy_file(*args) FileUtils.copy_file(self, *args) end # FileUtils.remove_dir def remove_dir(*args) FileUtils.remove_dir(self, *args) end # FileUtils.remove_file def remove_file(*args) FileUtils.remove_dir(self, *args) end # FileUtils.copy_entry def copy_entry(*args) FileUtils.copy_entry(self, *args) end end module Kernel # Usage: pn{ path } # # A shortcut for Pathname.new # def pn instance_eval{ Pathname.new(yield) } end begin remove_method(:Pathname) rescue NoMethodError, NameError # Do nothing, not defined. end # Synonym for Pathname.new # def Pathname(path) Pathname.new(path) end end class String # Convert a string directly into a Pathname object. def to_path Pathname.new(self) end end pathname2-1.8.0/test/0000755000004100000410000000000012734555701014417 5ustar www-datawww-datapathname2-1.8.0/test/windows/0000755000004100000410000000000012734555701016111 5ustar www-datawww-datapathname2-1.8.0/test/windows/test_misc.rb0000644000004100000410000000160012734555701020425 0ustar www-datawww-data######################################################################## # test_misc.rb # # Test suite for miscellaneous items that didn't warrant their own # test file. ######################################################################## require 'pathname2' require 'test-unit' class MyPathname < Pathname; end class TC_Pathname_Misc < Test::Unit::TestCase def setup @mypath = MyPathname.new(Dir.pwd) end test "subclasses return instances of that subclass" do assert_kind_of(MyPathname, @mypath) assert_kind_of(MyPathname, @mypath + MyPathname.new('foo')) assert_kind_of(MyPathname, @mypath.realpath) end test "custom pn method works as expected" do assert_respond_to(Kernel, :pn) assert_nothing_raised{ pn{'c:\foo'} } assert_kind_of(Pathname, pn{'c:\foo'}) assert_equal('c:\foo', pn{'c:\foo'}) end def teardown @mypath = nil end end pathname2-1.8.0/test/windows/test_children.rb0000644000004100000410000000214012734555701021262 0ustar www-datawww-data######################################################################## # test_children.rb # # Test suite for the Pathname#children method. ######################################################################## require 'pathname2' require 'test-unit' class TC_Pathname_Children < Test::Unit::TestCase def setup @dir = 'foo' @path = Pathname.new(File.dirname(File.dirname(__FILE__))) Dir.mkdir(@dir) Dir.chdir(@dir){ FileUtils.touch('alpha') FileUtils.touch('beta') FileUtils.touch('gamma') } end test "children basic functionality" do assert_respond_to(@path, :children) assert_nothing_raised{ @path.children{} } assert_kind_of(Array, @path.children) end test "children method returns expected results" do path = Pathname.new(@dir) assert_equal(%w[foo\alpha foo\beta foo\gamma], path.children) end test "each result of the children method is a Pathname object" do path = Pathname.new(@dir) assert_kind_of(Pathname, path.children.first) end def teardown FileUtils.rm_rf(@dir) if File.exist?(@dir) @path = nil end end pathname2-1.8.0/test/windows/test_join.rb0000644000004100000410000000326412734555701020441 0ustar www-datawww-data######################################################################## # test_join.rb # # Test suite for the Pathname#join method. ######################################################################## require 'test-unit' require 'pathname2' class TC_Pathname_Join < Test::Unit::TestCase def setup @apath = Pathname.new("C:\\foo\\bar") @rpath = Pathname.new("foo\\bar\\baz") end def assert_pathname_join(final, initial, *rest) a = Pathname.new(final) b = Pathname.new(initial) assert_equal(a, b.join(*rest)) end test "join method accepts one or more arguments" do assert_nothing_raised{ @apath.join("foo") } assert_nothing_raised{ @apath.join("foo", "bar") } assert_nothing_raised{ @apath.join("foo", "bar", "baz") } end test "join method returns expected results when joining relative paths to an absolute path" do assert_pathname_join("C:\\foo", "C:\\", "foo") assert_pathname_join("C:\\foo\\bar", "C:\\foo", "bar") assert_pathname_join("C:\\foo\\bar\\baz", "C:\\foo", "bar", "baz") end test "join method returns expected results when joining relative paths to a relative path" do assert_pathname_join("foo\\bar", "foo", "bar") assert_pathname_join("foo\\bar\\baz", "foo", "bar", "baz") end test "join method returns expected results when joining an absolute path to an absolute path" do assert_pathname_join("D:\\", "C:\\", "D:\\") assert_pathname_join("D:\\foo", "C:\\", "D:\\", "foo") assert_pathname_join("D:\\", "C:\\", "foo", "bar", "D:\\") end test "join returns an instance of Pathname" do assert_kind_of(Pathname, @apath.join("foo")) end def teardown @apath = nil @rpath = nil end end pathname2-1.8.0/test/windows/test_is_absolute.rb0000644000004100000410000000244012734555701022006 0ustar www-datawww-data######################################################################## # test_is_absolute.rb # # Test suite for the Pathname#absolute method ######################################################################## require 'test-unit' require 'pathname2' class TC_Pathname_IsAbsolute < Test::Unit::TestCase def setup @abs_std = Pathname.new("C:/foo/bar/baz") @abs_unc = Pathname.new("//foo/bar/baz") end test "absolute? basic functionality" do assert_respond_to(@abs_std, :absolute?) assert_nothing_raised{ @abs_std.absolute? } assert_boolean(@abs_std.absolute?) end test "absolute? method returns true for absolute paths" do assert_true(@abs_std.absolute?) assert_true(@abs_unc.absolute?) end test "absolute? method returns false for non-absolute paths" do assert_false(Pathname.new("foo").absolute?) assert_false(Pathname.new("foo/bar").absolute?) end test "absolute? method returns false for empty path" do assert_false(Pathname.new("").absolute?) end test "absolute? method is not destructive" do str = 'C:/foo' path = Pathname.new(str) assert_nothing_raised{ path.absolute? } assert_equal('C:\foo', path.to_s) assert_equal('C:/foo', str) end def teardown @std_absolute = nil @unc_absolute = nil end end pathname2-1.8.0/test/windows/test_facade.rb0000644000004100000410000000333412734555701020703 0ustar www-datawww-data######################################################################## # test_facade.rb # # Test suite for the various facade methods. ######################################################################## require 'test-unit' require 'pathname2' class TC_Pathname_Facade < Test::Unit::TestCase def setup @path = Pathname.new("C:/Program Files") end test "file facade methods are defined" do File.methods(false).each{ |m| assert_respond_to(@path, m.to_sym) } end test "dir facade methods are defined" do Dir.methods(false).each{ |m| assert_respond_to(@path, m.to_sym) } end test "fileutils facade methods are defined" do methods = FileUtils.public_instance_methods methods -= File.methods(false) methods -= Dir.methods(false) # Ruby 1.9.x and 2.0 incorrectly made some of these methods public methods.delete_if{ |m| m =~ /stream|^ln|identical\?|mode_to_s|^sh|ruby|safe_ln|split_all/i } methods.each{ |method| assert_respond_to(@path, method.to_sym) } end test "find facade works as expected" do assert_respond_to(@path, :find) assert_nothing_raised{ @path.find{} } Pathname.new(Dir.pwd).find{ |f| Find.prune if f.match("git") assert_kind_of(Pathname, f) } end test "custom io methods are defined" do assert_respond_to(@path, :foreach) assert_respond_to(@path, :read) assert_respond_to(@path, :readlines) assert_respond_to(@path, :sysopen) end test "exist? facade works as expected" do assert_respond_to(@path, :exist?) assert_nothing_raised{ @path.exist? } assert_true(Pathname.new("C:\\").exist?) assert_false(Pathname.new("X:\\foo\\bar\\baz").exist?) end def teardown @path = nil end end pathname2-1.8.0/test/windows/test_undecorate_bang.rb0000644000004100000410000000331312734555701022615 0ustar www-datawww-data######################################################################## # test_undecorate_bang.rb # # Test suite for the Pathname#undecorate! method ######################################################################## require 'test-unit' require 'pathname2' class TC_Pathname_UndecorateBang < Test::Unit::TestCase def setup @std = Pathname.new('C:/Path/File.txt') end test "undecorate! basic functionality" do assert_respond_to(@std, :undecorate!) assert_nothing_raised{ @std.undecorate! } end test "undecorate! returns a Pathname object" do assert_kind_of(Pathname, @std.undecorate!) end test "undecorate! method returns an already undecorated path unchanged" do assert_equal('C:\Path\File.txt', Pathname.new('C:\Path\File.txt').undecorate!) assert_equal('\\foo\bar', Pathname.new('\\foo\bar').undecorate!) end test "undecorate! returns expected result for standard path" do assert_equal('C:\Path\File', Pathname.new('C:\Path\File[12]').undecorate!) assert_equal('C:\Path\[3].txt', Pathname.new('C:\Path\[3].txt').undecorate!) end test "undecorate! returns expected result for UNC path" do assert_equal('\\foo\bar.txt',Pathname.new('\\foo\bar[5].txt').undecorate!) assert_equal('\\foo\bar', Pathname.new('\\foo\bar[5]').undecorate!) end test "undecorate! does not modify the original string" do str = 'C:/Path/File.txt' assert_nothing_raised{ Pathname.new(str).undecorate } assert_equal('C:/Path/File.txt', str) end test "undecorate does modify the object itself" do path = Pathname.new('C:\Path\File[12]') assert_nothing_raised{ path.undecorate! } assert_equal('C:\Path\File', path) end def teardown @std = nil end end pathname2-1.8.0/test/windows/test_parent.rb0000644000004100000410000000211012734555701020760 0ustar www-datawww-data######################################################################## # test_parent.rb # # Test suite for the Pathname#parent method. ######################################################################## require 'test-unit' require 'pathname2' class TC_Pathname_Parent < Test::Unit::TestCase def setup @path = Pathname.new("C:\\foo\\bar\\baz") end test "parent basic functionality" do assert_respond_to(@path, :parent) assert_nothing_raised{ @path.parent } assert_kind_of(Pathname, @path.parent) end test "parent returns expected results for an absolute path" do assert_equal("C:\\foo\\bar", Pathname.new("C:\\foo\\bar\\baz").parent) assert_equal("C:\\", Pathname.new("C:\\foo").parent) end test "parent returns expected results for a relative path" do assert_equal("foo", Pathname.new("foo\\bar").parent) end test "parent method returns root if already a root path" do assert_equal("C:\\", Pathname.new("C:\\").parent) assert_equal("\\\\foo\\bar", Pathname.new("//foo/bar").parent) end def teardown @path = nil end end pathname2-1.8.0/test/windows/test_relative_path_from.rb0000644000004100000410000000441212734555701023350 0ustar www-datawww-data######################################################################## # test_relative_path_from.rb # # Test suite for the Pathname#relative_path_from method. ######################################################################## require 'test-unit' require 'pathname2' class TC_Pathname_RelativePathFrom < Test::Unit::TestCase def assert_relpath(result, dest, base) assert_equal(result, Pathname.new(dest).relative_path_from(base)) end def assert_relative_path_error(to, from) assert_raise(ArgumentError){ Pathname.new(to).relative_path_from(from) } end test "relative_path_from works as expected between two relative paths" do assert_relpath("..\\a", 'a', 'b') assert_relpath("..\\a", 'a', 'b/') assert_relpath("..\\a", 'a/', 'b') assert_relpath("..\\a", 'a/', 'b/') assert_relpath("..\\b", "a\\b", "a\\c") assert_relpath("..\\a", "..\\a", "..\\b") assert_relpath("..\\b\\c", "a\\b\\c", "a\\d") assert_relpath("..", "a\\..", "a") assert_relpath(".", "a\\..\\b", "b") assert_relpath("a", "a", "b\\..") assert_relpath("b\\c", "b\\c", "b\\..") end test "relative_path_from works as expected between two absolute paths" do assert_relpath("..\\a", "c:\\a", "c:\\b") assert_relpath("..\\a", "c:\\a", "c:\\b\\") assert_relpath("..\\a", "c:\\a\\", "c:\\b") assert_relpath("..\\a", "c:\\a\\", "c:\\b\\") assert_relpath("c\\d", "c:\\a\\b\\c\\d", "c:\\a\\b") assert_relpath("..\\..", "c:\\a\\b", "c:\\a\\b\\c\\d") assert_relpath("..\\..\\..\\..\\e", "c:\\e", "c:\\a\\b\\c\\d") assert_relpath("..\\a", "c:\\..\\a", "c:\\b") assert_relpath(".", "c:\\a\\..\\..\\b", "c:\\b") end test "relative_path_from works as expected between for . and .." do assert_relpath("a", "a", ".") assert_relpath("..", ".", "a") assert_relpath(".", ".", ".") assert_relpath(".", "..", "..") assert_relpath("..", "..", ".") end test "relative_path_from is not allowed between relative and absolute paths" do assert_relative_path_error("c:\\", ".") assert_relative_path_error(".", "c:\\") assert_relative_path_error("a", "..") assert_relative_path_error(".", "..") assert_relative_path_error("C:\\Temp", "D:\\Temp") assert_relative_path_error("\\\\Server\\Temp", "D:\\Temp") end end pathname2-1.8.0/test/windows/test_descend.rb0000644000004100000410000000260512734555701021105 0ustar www-datawww-data######################################################################## # test_descend.rb # # Test suite for the Pathname#descend method. ######################################################################## require 'pathname2' require 'test-unit' class TC_Pathname_Descend < Test::Unit::TestCase def setup @path = Pathname.new("C:\\foo\\bar\\baz") end test "descend basic functionality" do assert_respond_to(@path, :descend) assert_nothing_raised{ @path.descend{} } end test "descend works as expected on a standard absolute path" do array = [] @path.descend{ |e| array << e } assert_equal('C:', array[0]) assert_equal('C:\foo', array[1]) assert_equal('C:\foo\bar', array[2]) assert_equal('C:\foo\bar\baz', array[3]) end test "descend works as expected on a UNC path" do array = [] Pathname.new('//foo/bar/baz').descend{ |e| array << e } assert_equal("\\\\foo\\bar", array[0]) assert_equal("\\\\foo\\bar\\baz", array[1]) end test "descend works as expected on a relative path" do array = [] Pathname.new('foo/bar/baz').descend{ |e| array << e } assert_equal('foo', array[0]) assert_equal('foo\bar', array[1]) assert_equal('foo\bar\baz', array[2]) end test "descend does not modify the receiver" do @path.descend{} assert_equal('C:\foo\bar\baz', @path) end def teardown @path = nil end end pathname2-1.8.0/test/windows/test_pstrip.rb0000644000004100000410000000245112734555701021020 0ustar www-datawww-data######################################################################## # test_pstrip.rb # # Test suite for the Pathname#pstrip method ######################################################################## require 'test-unit' require 'pathname2' class TC_Pathname_Pstrip < Test::Unit::TestCase def setup @path = Pathname.new("C:/Program Files////") end test "pstrip basic functionality" do assert_respond_to(@path, :pstrip) assert_nothing_raised{ @path.pstrip } assert_kind_of(Pathname, @path.pstrip) end test "pstrip returns expected result for path with trailing slashes" do assert_equal("C:\\Program Files", @path.pstrip) assert_equal("C:\\Program Files", Pathname.new("C:\\Program Files\\\\").pstrip) assert_equal("C:\\Program Files", Pathname.new("C:\\Program Files//\\").pstrip) end test "pstrip returns the path as is if it does not contain a trailing slash" do assert_equal("C:\\Program Files", Pathname.new("C:\\Program Files").pstrip) assert_equal("", Pathname.new("").pstrip) end test "pstrip method is not destructive" do str = 'C:/Program Files////' assert_nothing_raised{ Pathname.new(str).pstrip } assert_equal('C:/Program Files////', str) end def teardown @abs_path = nil @unc_path = nil @rel_path = nil end end pathname2-1.8.0/test/windows/test_root.rb0000644000004100000410000000337012734555701020463 0ustar www-datawww-data######################################################################## # test_root.rb # # Test suite for the Pathname#root method ######################################################################## require 'test-unit' require 'pathname2' class TC_Pathname_Root < Test::Unit::TestCase def setup @abs_path = Pathname.new("C:\\Program Files") @unc_path = Pathname.new("\\\\foo\\bar\\baz") @rel_path = Pathname.new("foo\\bar\\baz") end test "root method returns expected results for absolute paths" do assert_equal("C:\\", @abs_path.root) end test "root method returns expected results for paths with forward slashes" do assert_equal("C:\\", Pathname.new("C:/Program Files").root) end test "root method returns expected results for unc paths" do assert_equal("\\\\foo\\bar", @unc_path.root) assert_equal("\\\\foo", Pathname.new("\\\\foo").root) assert_equal("\\\\", Pathname.new("\\\\").root) end test "root method returns dot for relative paths" do assert_equal('.', @rel_path.root) end test "root method returns expected result for root path" do assert_equal("Z:\\", Pathname.new("Z:\\").root) assert_equal("\\\\foo\\bar", Pathname.new("\\\\foo\\bar").root) end test "root method returns expected result for empty string" do assert_equal(".", Pathname.new("").root) end test "root method returns expected result for dot and dotdot" do assert_equal(".", Pathname.new("..").root) assert_equal(".", Pathname.new(".").root) end test "root method is not destructive" do str = 'C:/Program Files' assert_nothing_raised{ Pathname.new(str).root } assert_equal('C:/Program Files', str) end def teardown @abs_path = nil @unc_path = nil @rel_path = nil end end pathname2-1.8.0/test/windows/test_short_path.rb0000644000004100000410000000225012734555701021647 0ustar www-datawww-data######################################################################## # test_short_path.rb # # Test suite for the Pathname#short_path method ######################################################################## require 'test-unit' require 'pathname2' class TC_Pathname_ShortPath < Test::Unit::TestCase def setup @abs_path = Pathname.new("C:\\Program Files") end test "short_path basic functionality" do assert_respond_to(@abs_path, :short_path) assert_nothing_raised{ @abs_path.short_path } assert_kind_of(String, @abs_path.short_path) end test "short_path returns the expected result" do assert_equal("C:\\PROGRA~1", @abs_path.short_path) end test "short_path returns the same string if it's already short" do assert_equal("C:\\", Pathname.new("C:/").short_path) end test "short_path fails if the path does not exist" do assert_raise(Errno::ESRCH){ Pathname.new("C:/Bogus/AlsoBogus").short_path } end test "short_path method is not destructive" do str = 'C:/Program Files' assert_nothing_raised{ Pathname.new(str).short_path } assert_equal('C:/Program Files', str) end def teardown @abs_path = nil end end pathname2-1.8.0/test/windows/test_drive_number.rb0000644000004100000410000000342012734555701022155 0ustar www-datawww-data######################################################################## # test_drive_number.rb # # Test suite for the Pathname#drive_number method ######################################################################## require 'test-unit' require 'pathname2' class TC_Pathname_DriveNumber < Test::Unit::TestCase def setup @abs_path = Pathname.new("C:\\Program Files") @unc_path = Pathname.new("\\\\foo\\bar\\baz") @rel_path = Pathname.new("foo\\bar\\baz") end test "drive_number method returns expected results for absolute paths" do assert_equal(2, @abs_path.drive_number) end test "drive_number method returns expected results for paths with forward slashes" do assert_equal(2, Pathname.new("C:/Program Files").drive_number) end test "drive_number method returns expected results for unc paths" do assert_nil(@unc_path.drive_number) assert_nil(Pathname.new("\\\\foo").drive_number) assert_nil(Pathname.new("\\\\").drive_number) end test "drive_number method returns dot for relative paths" do assert_nil(@rel_path.drive_number) end test "drive_number method returns expected result for root path" do assert_equal(25, Pathname.new("Z:\\").drive_number) end test "drive_number method returns expected result for empty string" do assert_nil(Pathname.new("").drive_number) end test "drive_number method returns expected result for dot and dotdot" do assert_nil(Pathname.new(".").drive_number) assert_nil(Pathname.new("..").drive_number) end test "drive_number method is not destructive" do str = 'C:/Program Files' assert_nothing_raised{ Pathname.new(str).drive_number } assert_equal('C:/Program Files', str) end def teardown @abs_path = nil @unc_path = nil @rel_path = nil end end pathname2-1.8.0/test/windows/test_is_unc.rb0000644000004100000410000000312112734555701020752 0ustar www-datawww-data######################################################################## # test_is_unc.rb # # Test suite for the Pathname#unc? method ######################################################################## require 'test-unit' require 'pathname2' class TC_Pathname_IsUNC < Test::Unit::TestCase def setup @abs_path = Pathname.new("C:\\Program Files") @unc_path = Pathname.new("\\\\foo\\bar\\baz") @rel_path = Pathname.new("foo\\bar\\baz") end test "unc? basic functionality" do assert_respond_to(@unc_path, :unc?) assert_nothing_raised{ @unc_path.unc? } assert_boolean(@unc_path.unc?) end test "unc? method returns false for non-unc paths" do assert_false(Pathname.new("C:\\").unc?) assert_false(Pathname.new("C:\\Program Files").unc?) assert_false(Pathname.new("C:\\\\Program Files").unc?) assert_false(Pathname.new("C:/Program Files/File.txt").unc?) assert_false(Pathname.new("C:\\Program Files\\File[12].txt").unc?) assert_false(Pathname.new("foo\\bar").unc?) assert_false(Pathname.new(".").unc?) end test "unc? method returns true for unc paths" do assert_true(Pathname.new("\\\\foo\\bar").unc?) assert_true(Pathname.new("//foo/bar").unc?) assert_true(Pathname.new("\\\\foo\\bar\\baz").unc?) assert_true(Pathname.new("\\\\foo").unc?) assert_true(Pathname.new("\\\\").unc?) end test "unc? method is not destructive" do str = '//foo/bar' assert_nothing_raised{ Pathname.new(str).unc? } assert_equal('//foo/bar', str) end def teardown @abs_path = nil @unc_path = nil @rel_path = nil end end pathname2-1.8.0/test/windows/test_ascend.rb0000644000004100000410000000256712734555701020744 0ustar www-datawww-data######################################################################## # test_ascend.rb # # Test suite for the Pathname#ascend method. ######################################################################## require 'pathname2' require 'test-unit' class TC_Pathname_Ascend < Test::Unit::TestCase def setup @path = Pathname.new("C:\\foo\\bar\\baz") end test "ascend basic functionality" do assert_respond_to(@path, :ascend) assert_nothing_raised{ @path.ascend{} } end test "ascend works as expected on a standard absolute path" do array = [] @path.ascend{ |e| array << e } assert_equal('C:\foo\bar\baz', array[0]) assert_equal('C:\foo\bar', array[1]) assert_equal('C:\foo', array[2]) assert_equal('C:', array[3]) end test "ascend works as expected on a UNC path" do array = [] Pathname.new('//foo/bar/baz').ascend{ |e| array << e } assert_equal("\\\\foo\\bar\\baz", array[0]) assert_equal("\\\\foo\\bar", array[1]) end test "ascend works as expected on a relative path" do array = [] Pathname.new('foo/bar/baz').ascend{ |e| array << e } assert_equal('foo\bar\baz', array[0]) assert_equal('foo\bar', array[1]) assert_equal('foo', array[2]) end test "ascend does not modify the receiver" do @path.ascend{} assert_equal('C:\foo\bar\baz', @path) end def teardown @path = nil end end pathname2-1.8.0/test/windows/test_clean_bang.rb0000644000004100000410000000315712734555701021554 0ustar www-datawww-data######################################################################## # test_clean_bang.rb # # Test suite for the Pathname#clean! method. ######################################################################## require 'test-unit' require 'pathname2' class TC_Pathname_CleanBang < Test::Unit::TestCase def setup @path = Pathname.new("C:\\foo\\..\\bar\\.\\baz") end test "clean basic functionality" do assert_respond_to(@path, :clean!) assert_nothing_raised{ @path.clean! } assert_kind_of(Pathname, @path.clean!) end test "clean returns expected results for unclean paths" do assert_equal("C:\\a\\c", Pathname.new("C:\\a\\.\\b\\..\\c").clean!) assert_equal("C:\\a", Pathname.new("C:\\.\\a").clean!) assert_equal("C:\\a\\b", Pathname.new("C:\\a\\.\\b").clean!) assert_equal("C:\\b", Pathname.new("C:\\a\\..\\b").clean!) assert_equal("C:\\a", Pathname.new("C:\\a\\.").clean!) assert_equal("C:\\d", Pathname.new("C:\\..\\..\\..\\d").clean!) end test "clean returns already clean paths unmodified" do assert_equal("C:\\", Pathname.new("C:\\").clean!) assert_equal("C:\\a", Pathname.new("C:\\a").clean!) assert_equal("C:\\a\\", Pathname.new("C:\\a\\").clean!) assert_equal("\\\\foo\\bar", Pathname.new("\\\\foo\\bar").clean!) assert_equal("a", Pathname.new("a").clean!) end test "clean returns a slash for . and .." do assert_equal("\\", Pathname.new(".").clean!) assert_equal("\\", Pathname.new("..").clean!) end test "clean! modifies receiver" do @path.clean! assert_equal("C:\\bar\\baz", @path) end def teardown @path = nil end end pathname2-1.8.0/test/windows/test_each.rb0000644000004100000410000000123612734555701020377 0ustar www-datawww-data######################################################################## # test_each.rb # # Test suite for the Pathname#each method. ######################################################################## require 'pathname2' require 'test-unit' class TC_Pathname_Each < Test::Unit::TestCase def setup @path = Pathname.new("C:/Users/foo/bar") end test "each basic functionality" do assert_respond_to(@path, :each) assert_nothing_raised{ @path.each{} } end test "each returns the expected results" do arr = [] @path.each{ |e| arr << e } assert_equal(['C:', 'Users', 'foo', 'bar'], arr) end def teardown @path = nil end end pathname2-1.8.0/test/windows/test_append.rb0000644000004100000410000000363312734555701020751 0ustar www-datawww-data######################################################################## # test_append.rb # # Test suite for the Pathname#append method. ######################################################################## require 'test-unit' require 'pathname2' class TC_Pathname_Append < Test::Unit::TestCase def setup @abs_path = Pathname.new("C:\\foo\\bar") @rel_path = Pathname.new("foo\\bar\\baz") end def assert_pathname_plus(a, b, c) a = Pathname.new(a) b = Pathname.new(b) c = Pathname.new(c) assert_equal(a, b + c) end test "appending a string to an absolute path works as expected" do assert_pathname_plus("C:\\a\\b", "C:\\a", "b") assert_pathname_plus("C:\\b", "a", "C:\\b") assert_pathname_plus("a\\b", "a", "b") assert_pathname_plus("C:\\b", "C:\\a", "..\\b") assert_pathname_plus("C:\\a\\b", "C:\\a\\.", "\\b") assert_pathname_plus("C:\\a\\b.txt", "C:\\a", "b.txt") end test "appending a string to a UNC path works as expected" do assert_pathname_plus("\\\\foo\\bar", "\\\\foo", "bar") assert_pathname_plus("\\\\foo", "\\\\", "foo") assert_pathname_plus("\\\\", "\\\\", "") assert_pathname_plus("\\\\foo\\baz", "\\\\foo\\bar", "\\..\\baz") assert_pathname_plus("\\\\", "\\\\", "..\\..\\..\\..") end test "appending a plain string to a path works as expected" do assert_nothing_raised{ @abs_path + "bar" } assert_equal('C:\foo\bar\baz', @abs_path + 'baz') assert_equal('C:\foo\bar', @abs_path) end test "appending an absolute path results in that absolute path" do assert_pathname_plus('C:\foo\bar', @rel_path, @abs_path) end test "neither receiver nor argument are modified" do assert_nothing_raised{ @abs_path + @rel_path } assert_equal('C:\foo\bar\foo\bar\baz', @abs_path + @rel_path) assert_equal('C:\foo\bar', @abs_path) assert_equal('foo\bar\baz', @rel_path) end def teardown @path = nil end end pathname2-1.8.0/test/windows/test_aref.rb0000644000004100000410000000214412734555701020413 0ustar www-datawww-data######################################################################## # test_aref.rb # # Test suite for the Pathname#[] method. ######################################################################## require 'test-unit' require 'pathname2' class TC_Pathname_Aref < Test::Unit::TestCase def setup @path = Pathname.new("C:/Program Files/Windows NT/Accessories") end test "[] with index works as expected" do assert_equal("C:", @path[0]) assert_equal("Program Files", @path[1]) assert_equal("Accessories", @path[-1]) assert_nil(@path[10]) end test "[] with range argument works as expected" do assert_equal("C:\\Program Files", @path[0..1]) assert_equal("C:\\Program Files\\Windows NT", @path[0..2]) assert_equal("Program Files\\Windows NT", @path[1..2]) #assert_equal(@path, @path[0..-1]) # TODO: Spews tons of warnings end test "[] with index and length works as expected" do assert_equal("C:", @path[0,1]) assert_equal("C:\\Program Files", @path[0,2]) assert_equal("Program Files\\Windows NT", @path[1,2]) end def teardown @path = nil end end pathname2-1.8.0/test/windows/test_undecorate.rb0000644000004100000410000000276512734555701021640 0ustar www-datawww-data######################################################################## # test_undecorate.rb # # Test suite for the Pathname#undecorate method ######################################################################## require 'test-unit' require 'pathname2' class TC_Pathname_Undecorate < Test::Unit::TestCase def setup @std = Pathname.new('C:/Path/File.txt') end test "undecorate basic functionality" do assert_respond_to(@std, :undecorate) assert_nothing_raised{ @std.undecorate } end test "undecorate returns a Pathname object" do assert_kind_of(Pathname, @std.undecorate) end test "undecorate method returns an already undecorated path unchanged" do assert_equal('C:\Path\File.txt', Pathname.new('C:\Path\File.txt').undecorate) assert_equal('\\foo\bar', Pathname.new('\\foo\bar').undecorate) end test "undecorate returns expected result for standard path" do assert_equal('C:\Path\File', Pathname.new('C:\Path\File[12]').undecorate) assert_equal('C:\Path\[3].txt', Pathname.new('C:\Path\[3].txt').undecorate) end test "undecorate returns expected result for UNC path" do assert_equal('\\foo\bar.txt',Pathname.new('\\foo\bar[5].txt').undecorate) assert_equal('\\foo\bar', Pathname.new('\\foo\bar[5]').undecorate) end test "undecorate does not modify the original string" do str = 'C:/Path/File.txt' assert_nothing_raised{ Pathname.new(str).undecorate } assert_equal('C:/Path/File.txt', str) end def teardown @std = nil end end pathname2-1.8.0/test/windows/test_to_a.rb0000644000004100000410000000271012734555701020417 0ustar www-datawww-data######################################################################## # test_to_a.rb # # Test suite for the Pathname#to_a method. ######################################################################## require 'test-unit' require 'pathname2' class TC_Pathname_ToA < Test::Unit::TestCase def setup @path = Pathname.new('C:/Program Files/foo') end test "to_a basic functionality" do assert_respond_to(@path, :to_a) assert_nothing_raised{ @path.to_a } assert_kind_of(Array, @path.to_a) end test "to_a returns the expected results for standard paths" do assert_equal(['C:'], Pathname.new('C:/').to_a) assert_equal(['C:', 'Program Files'], Pathname.new('C:/Program Files').to_a) assert_equal(['C:', 'Program Files', 'Stuff'], Pathname.new('C:/Program Files/Stuff').to_a) assert_equal(['C:', 'Users'], Pathname.new("C:\\Users").to_a) end test "to_a returns the expected results for unc paths" do assert_equal(['foo', 'bar', 'baz'], Pathname.new('//foo/bar/baz').to_a) assert_equal(['foo', 'bar'], Pathname.new('//foo/bar').to_a) assert_equal(['foo'], Pathname.new('//foo').to_a) end test "to_a returns the expected results for empty strings and empty unc paths" do assert_equal([], Pathname.new('').to_a) assert_equal([], Pathname.new('//').to_a) end test "to_a does not modify receiver" do @path.to_a assert_equal('C:\Program Files\foo', @path) end def teardown @path = nil end end pathname2-1.8.0/test/windows/test_long_path.rb0000644000004100000410000000226212734555701021452 0ustar www-datawww-data######################################################################## # test_long_path.rb # # Test suite for the Pathname#long_path method ######################################################################## require 'test-unit' require 'pathname2' class TC_Pathname_LongPath < Test::Unit::TestCase def setup @abs_path = Pathname.new("C:\\PROGRA~1") end test "long_path basic functionality" do assert_respond_to(@abs_path, :long_path) assert_nothing_raised{ @abs_path.long_path } assert_kind_of(String, @abs_path.long_path) end test "long_path returns the expected result" do assert_equal("C:\\Program Files", @abs_path.long_path) end test "long_path returns the same string if it's already long" do assert_equal("C:\\Program Files", Pathname.new("C:/Program Files").long_path) end test "long_path fails if the path does not exist" do assert_raise(Errno::ESRCH){ Pathname.new("C:/Bogus/AlsoBogus").long_path } end test "long_path method is not destructive" do str = 'C:/Program Files' assert_nothing_raised{ Pathname.new(str).long_path } assert_equal('C:/Program Files', str) end def teardown @abs_path = nil end end pathname2-1.8.0/test/windows/test_constructor.rb0000644000004100000410000000263612734555701022071 0ustar www-datawww-data######################################################################## # test_constructor.rb # # Various tests for the Pathname.new method. ######################################################################## require 'pathname2' require 'test-unit' class TC_Pathname_Constructor < Test::Unit::TestCase def setup @abs_path = "C:/Users" @rel_path = "Users" @url_path = "file:///C:/Documents%20and%20Settings" end test "constructor handles absolute paths properly" do assert_nothing_raised{ Pathname.new(@abs_path) } assert_equal("C:\\Users", Pathname.new(@abs_path).to_s) end test "constructor handles relative paths properly" do assert_nothing_raised{ Pathname.new(@rel_path) } assert_equal("Users", Pathname.new(@rel_path).to_s) end test "constructor handles file URL's properly" do assert_nothing_raised{ Pathname.new(@url_path) } assert_equal("C:\\Documents and Settings", Pathname.new(@url_path).to_s) end test "constructor returns a Pathname object" do assert_kind_of(Pathname, Pathname.new(@abs_path)) end test "constructor handles frozen arguments without issue" do assert_nothing_raised{ Pathname.new(@abs_path.freeze) } end test "constructor raises an error if string argument is too long" do assert_raise(ArgumentError){ Pathname.new("foo" * 1000) } end def teardown @url_path = nil @rel_path = nil @abs_path = nil end end pathname2-1.8.0/test/windows/test_pstrip_bang.rb0000644000004100000410000000275312734555701022014 0ustar www-datawww-data######################################################################## # test_pstrip_bang.rb # # Test suite for the Pathname#pstrip! method ######################################################################## require 'test-unit' require 'pathname2' class TC_Pathname_PstripBang < Test::Unit::TestCase def setup @path = Pathname.new("C:/Program Files////") end test "pstrip! basic functionality" do assert_respond_to(@path, :pstrip!) assert_nothing_raised{ @path.pstrip! } assert_kind_of(Pathname, @path.pstrip!) end test "pstrip! returns expected result for path with trailing slashes" do assert_equal("C:\\Program Files", @path.pstrip!) assert_equal("C:\\Program Files", Pathname.new("C:\\Program Files\\\\").pstrip!) assert_equal("C:\\Program Files", Pathname.new("C:\\Program Files//\\").pstrip!) end test "pstrip! returns the path as is if it does not contain a trailing slash" do assert_equal("C:\\Program Files", Pathname.new("C:\\Program Files").pstrip!) assert_equal("", Pathname.new("").pstrip!) end test "pstrip! alters pathname object" do path = Pathname.new('C:/Program Files////') assert_nothing_raised{ path.pstrip! } assert_equal('C:\Program Files', path.to_s) end test "pstrip! method does not modify original constructor argument" do str = 'C:/Program Files////' assert_nothing_raised{ Pathname.new(str).pstrip! } assert_equal('C:/Program Files////', str) end def teardown @path = nil end end pathname2-1.8.0/test/windows/test_is_relative.rb0000644000004100000410000000235612734555701022011 0ustar www-datawww-data######################################################################## # test_is_relative.rb # # Test suite for the Pathname#relative method ######################################################################## require 'test-unit' require 'pathname2' class TC_Pathname_IsRelative < Test::Unit::TestCase def setup @relative = Pathname.new("foo/bar") @absolute = Pathname.new("C:/foo/bar") end test "relative? basic functionality" do assert_respond_to(@relative, :relative?) assert_nothing_raised{ @relative.relative? } assert_boolean(@relative.relative?) end test "relative? method returns true for relative paths" do assert_true(@relative.relative?) end test "relative? method returns false for non-relative paths" do assert_false(@absolute.relative?) assert_false(Pathname.new("//foo/bar").relative?) end test "relative? method returns true for empty path" do assert_true(Pathname.new("").relative?) end test "relative? method is not destructive" do str = 'C:/foo' path = Pathname.new(str) assert_nothing_raised{ path.relative? } assert_equal('C:\foo', path.to_s) assert_equal('C:/foo', str) end def teardown @std_relative = nil @unc_relative = nil end end pathname2-1.8.0/test/windows/test_realpath.rb0000644000004100000410000000201712734555701021275 0ustar www-datawww-data######################################################################## # test_realpath.rb # # Test suite for the Pathname#realpath method ######################################################################## require 'test-unit' require 'pathname2' class TC_Pathname_Realpath < Test::Unit::TestCase def setup @cwd = Dir.pwd.tr('/', "\\") @path = Pathname.new(Dir.pwd) end test "realpath basic functionality" do assert_respond_to(@path, :realpath) assert_nothing_raised{ @path.realpath } assert_kind_of(String, @path.realpath) end test "realpath returns the expected result" do assert_equal(@cwd, @path.realpath) end test "realpath fails if the path does not exist" do assert_raise(Errno::ENOENT){ Pathname.new("C:/Bogus/AlsoBogus").realpath } end test "realpath method is not destructive" do str = 'C:/Program Files' assert_nothing_raised{ Pathname.new(str).realpath } assert_equal('C:/Program Files', str) end def teardown @cwd = nil @path = nil end end pathname2-1.8.0/test/windows/test_is_root.rb0000644000004100000410000000222312734555701021152 0ustar www-datawww-data######################################################################## # test_is_root.rb # # Test suite for the Pathname#root method ######################################################################## require 'test-unit' require 'pathname2' class TC_Pathname_IsRoot < Test::Unit::TestCase def setup @std_root = Pathname.new("C:\\") @unc_root = Pathname.new("\\\\foo\\bar") end test "root? basic functionality" do assert_respond_to(@std_root, :root?) assert_nothing_raised{ @std_root.root? } assert_boolean(@std_root.root?) end test "root? method returns true for root paths" do assert_true(@std_root.root?) assert_true(@unc_root.root?) end test "root? method returns false for non-root paths" do assert_false(Pathname.new("C:/foo").root?) assert_false(Pathname.new("//foo/bar/baz").root?) assert_false(Pathname.new("").root?) end test "root? method is not destructive" do str = 'C:/foo' path = Pathname.new(str) assert_nothing_raised{ path.root } assert_equal('C:\foo', path.to_s) assert_equal('C:/foo', str) end def teardown @std_root = nil @unc_root = nil end end pathname2-1.8.0/test/windows/test_clean.rb0000644000004100000410000000314612734555701020563 0ustar www-datawww-data######################################################################## # test_clean.rb # # Test suite for the Pathname#clean method. ######################################################################## require 'test-unit' require 'pathname2' class TC_Pathname_Clean < Test::Unit::TestCase def setup @path = Pathname.new("C:\\foo\\..\\bar\\.\\baz") end test "clean basic functionality" do assert_respond_to(@path, :clean) assert_nothing_raised{ @path.clean } assert_kind_of(Pathname, @path.clean) end test "clean returns expected results for unclean paths" do assert_equal("C:\\a\\c", Pathname.new("C:\\a\\.\\b\\..\\c").clean) assert_equal("C:\\a", Pathname.new("C:\\.\\a").clean) assert_equal("C:\\a\\b", Pathname.new("C:\\a\\.\\b").clean) assert_equal("C:\\b", Pathname.new("C:\\a\\..\\b").clean) assert_equal("C:\\a", Pathname.new("C:\\a\\.").clean) assert_equal("C:\\d", Pathname.new("C:\\..\\..\\..\\d").clean) end test "clean returns already clean paths unmodified" do assert_equal("C:\\", Pathname.new("C:\\").clean) assert_equal("C:\\a", Pathname.new("C:\\a").clean) assert_equal("C:\\a\\", Pathname.new("C:\\a\\").clean) assert_equal("\\\\foo\\bar", Pathname.new("\\\\foo\\bar").clean) assert_equal("a", Pathname.new("a").clean) end test "clean returns a slash for . and .." do assert_equal("\\", Pathname.new(".").clean) assert_equal("\\", Pathname.new("..").clean) end test "clean does not modify receiver" do @path.clean assert_equal("C:\\foo\\..\\bar\\.\\baz", @path) end def teardown @path = nil end end pathname2-1.8.0/test/test_pathname.rb0000644000004100000410000003516212734555701017607 0ustar www-datawww-data############################################################################## # test_pathname.rb # # Test suite for the pathname library on unixy platforms. This test suite # should be run via the test rake task. ############################################################################## require 'pathname2' require 'fileutils' require 'rbconfig' require 'test-unit' include RbConfig class MyPathname < Pathname; end class TC_Pathname < Test::Unit::TestCase def self.startup Dir.chdir(File.expand_path(File.dirname(__FILE__))) @@pwd = Dir.pwd end def setup @abs_path = Pathname.new('/usr/local/bin') @rel_path = Pathname.new('usr/local/bin') @trl_path = Pathname.new('/usr/local/bin/') @mul_path = Pathname.new('/usr/local/lib/local/lib') @rul_path = Pathname.new('usr/local/lib/local/lib') @url_path = Pathname.new('file:///foo%20bar/baz') @cur_path = Pathname.new(@@pwd) @abs_array = [] @rel_array = [] @mypath = MyPathname.new('/usr/bin') @test_file = 'realpath_test.txt' @link_file = 'realpath_symlink.txt' @link_file2 = 'realpath_symlink2.txt' end # Convenience method to verify that the receiver was not modified # except perhaps slashes def assert_non_destructive assert_equal('/usr/local/bin', @abs_path) assert_equal('usr/local/bin', @rel_path) end # Convenience method for test_plus def assert_pathname_plus(a, b, c) a = Pathname.new(a) b = Pathname.new(b) c = Pathname.new(c) assert_equal(a, b + c) end # Convenience method for test_spaceship operator def assert_pathname_cmp(int, s1, s2) p1 = Pathname.new(s1) p2 = Pathname.new(s2) result = p1 <=> p2 assert_equal(int, result) end # Convenience method for test_relative_path_from def assert_relpath(result, dest, base) assert_equal(result, Pathname.new(dest).relative_path_from(base)) end # Convenience method for test_relative_path_from_expected_errors def assert_relpath_err(to, from) assert_raise(ArgumentError) { Pathname.new(to).relative_path_from(from) } end test "url_path returns expected result" do assert_equal('/foo bar/baz', @url_path) end test "realpath basic functionality" do FileUtils.touch(@test_file) && File.symlink(@test_file, @link_file) assert_respond_to(@abs_path, :realpath) assert_equal(@@pwd, Pathname.new('.').realpath) assert_kind_of(Pathname, Pathname.new(@link_file).realpath) end test "realpath returns expected result for simple symlink" do FileUtils.touch(@test_file) && File.symlink(@test_file, @link_file) assert_true(Pathname.new(@link_file) != Pathname.new(@link_file).realpath) assert_raises(Errno::ENOENT){ Pathname.new('../bogus').realpath } end test "realpath returns expected result for nested symlink" do FileUtils.touch(@test_file) && File.symlink(@test_file, @link_file) && File.symlink(@link_file, @link_file2) assert_true(Pathname.new(@link_file) != Pathname.new(@link_file2).realpath) assert_equal(Pathname.new(@link_file).realpath, Pathname.new(@link_file2).realpath) end # These tests taken directly from Tanaka's pathname.rb. The one failure # (commented out) is due to the fact that Tanaka's cleanpath method returns # the cleanpath for '../a' as '../a' (i.e. it does nothing) whereas mine # converts '../a' into just 'a'. Which is correct? I vote mine, because # I don't see how you can get 'more relative' from a relative path not # already in the pathname. # def test_relative_path_from assert_relpath('../a', 'a', 'b') assert_relpath('../a', 'a', 'b/') assert_relpath('../a', 'a/', 'b') assert_relpath('../a', 'a/', 'b/') assert_relpath('../a', '/a', '/b') assert_relpath('../a', '/a', '/b/') assert_relpath('../a', '/a/', '/b') assert_relpath('../a', '/a/', '/b/') assert_relpath('../b', 'a/b', 'a/c') assert_relpath('../a', '../a', '../b') assert_relpath('a', 'a', '.') assert_relpath('..', '.', 'a') assert_relpath('.', '.', '.') assert_relpath('.', '..', '..') assert_relpath('..', '..', '.') assert_relpath('c/d', '/a/b/c/d', '/a/b') assert_relpath('../..', '/a/b', '/a/b/c/d') assert_relpath('../../../../e', '/e', '/a/b/c/d') assert_relpath('../b/c', 'a/b/c', 'a/d') assert_relpath('../a', '/../a', '/b') #assert_relpath('../../a', '../a', 'b') # fails assert_relpath('.', '/a/../../b', '/b') assert_relpath('..', 'a/..', 'a') assert_relpath('.', 'a/../b', 'b') assert_relpath('a', 'a', 'b/..') assert_relpath('b/c', 'b/c', 'b/..') assert_relpath_err('/', '.') assert_relpath_err('.', '/') assert_relpath_err('a', '..') assert_relpath_err('.', '..') end def test_parent assert_respond_to(@abs_path, :parent) assert_equal('/usr/local', @abs_path.parent) assert_equal('usr/local', @rel_path.parent) assert_equal('/', Pathname.new('/').parent) end def test_pstrip assert_respond_to(@trl_path, :pstrip) assert_nothing_raised{ @trl_path.pstrip } assert_equal('/usr/local/bin', @trl_path.pstrip) assert_equal('/usr/local/bin/', @trl_path) end def test_pstrip_bang assert_respond_to(@trl_path, :pstrip!) assert_nothing_raised{ @trl_path.pstrip! } assert_equal('/usr/local/bin', @trl_path.pstrip!) assert_equal('/usr/local/bin', @trl_path) end def test_ascend assert_respond_to(@abs_path, :ascend) assert_nothing_raised{ @abs_path.ascend{} } @abs_path.ascend{ |path| @abs_array.push(path) } @rel_path.ascend{ |path| @rel_array.push(path) } assert_equal('/usr/local/bin', @abs_array[0]) assert_equal('/usr/local', @abs_array[1]) assert_equal('/usr', @abs_array[2]) assert_equal('/', @abs_array[3]) assert_equal(4, @abs_array.length) assert_equal('usr/local/bin', @rel_array[0]) assert_equal('usr/local', @rel_array[1]) assert_equal('usr', @rel_array[2]) assert_equal(3, @rel_array.length) assert_non_destructive end def test_descend assert_respond_to(@abs_path, :descend) assert_nothing_raised{ @abs_path.descend{} } @abs_path.descend{ |path| @abs_array.push(path) } @rel_path.descend{ |path| @rel_array.push(path) } assert_equal('/', @abs_array[0]) assert_equal('/usr', @abs_array[1]) assert_equal('/usr/local', @abs_array[2]) assert_equal('/usr/local/bin', @abs_array[3]) assert_equal(4, @abs_array.length) assert_equal('usr', @rel_array[0]) assert_equal('usr/local', @rel_array[1]) assert_equal('usr/local/bin', @rel_array[2]) assert_equal(3, @rel_array.length) assert_non_destructive end def test_children_with_directory assert_respond_to(@cur_path, :children) assert_nothing_raised{ @cur_path.children } assert_kind_of(Array, @cur_path.children) children = @cur_path.children.sort.reject{ |f| f.include?('git') || f.include?('.swp') } assert_equal( [ Dir.pwd + '/test_pathname.rb', Dir.pwd + '/test_version.rb', Dir.pwd + '/windows' ], children.sort ) end def test_children_without_directory assert_nothing_raised{ @cur_path.children(false) } children = @cur_path.children(false).reject{ |f| f.include?('git') || f.include?('.swp') } assert_equal(['test_pathname.rb', 'test_version.rb', 'windows'], children.sort) end def test_unc assert_raises(NotImplementedError){ @abs_path.unc? } end def test_enumerable assert_respond_to(@abs_path, :each) end def test_root assert_respond_to(@abs_path, :root) assert_nothing_raised{ @abs_path.root } assert_nothing_raised{ @rel_path.root } assert_equal('/', @abs_path.root) assert_equal('.', @rel_path.root) assert_non_destructive end def test_root? assert_respond_to(@abs_path, :root?) assert_nothing_raised{ @abs_path.root? } assert_nothing_raised{ @rel_path.root? } path1 = Pathname.new('/') path2 = Pathname.new('a') assert_equal(true, path1.root?) assert_equal(false, path2.root?) assert_non_destructive end def test_absolute assert_respond_to(@abs_path, :absolute?) assert_nothing_raised{ @abs_path.absolute? } assert_nothing_raised{ @rel_path.absolute? } assert_equal(true, @abs_path.absolute?) assert_equal(false, @rel_path.absolute?) assert_equal(true, Pathname.new('/usr/bin/ruby').absolute?) assert_equal(false, Pathname.new('foo').absolute?) assert_equal(false, Pathname.new('foo/bar').absolute?) assert_equal(false, Pathname.new('../foo/bar').absolute?) assert_non_destructive end def test_relative assert_respond_to(@abs_path, :relative?) assert_nothing_raised{ @abs_path.relative? } assert_nothing_raised{ @rel_path.relative? } assert_equal(false, @abs_path.relative?) assert_equal(true, @rel_path.relative?) assert_equal(false, Pathname.new('/usr/bin/ruby').relative?) assert_equal(true, Pathname.new('foo').relative?) assert_equal(true, Pathname.new('foo/bar').relative?) assert_equal(true, Pathname.new('../foo/bar').relative?) assert_non_destructive end def test_to_a assert_respond_to(@abs_path, :to_a) assert_nothing_raised{ @abs_path.to_a } assert_nothing_raised{ @rel_path.to_a } assert_kind_of(Array, @abs_path.to_a) assert_equal(%w/usr local bin/, @abs_path.to_a) assert_non_destructive end def test_spaceship_operator assert_respond_to(@abs_path, :<=>) assert_pathname_cmp( 0, '/foo/bar', '/foo/bar') assert_pathname_cmp(-1, '/foo/bar', '/foo/zap') assert_pathname_cmp( 1, '/foo/zap', '/foo/bar') assert_pathname_cmp(-1, 'foo', 'foo/') assert_pathname_cmp(-1, 'foo/', 'foo/bar') end def test_plus_operator assert_respond_to(@abs_path, :+) # Standard stuff assert_pathname_plus('/foo/bar', '/foo', 'bar') assert_pathname_plus('foo/bar', 'foo', 'bar') assert_pathname_plus('foo', 'foo', '.') assert_pathname_plus('foo', '.', 'foo') assert_pathname_plus('/foo', 'bar', '/foo') assert_pathname_plus('foo', 'foo/bar', '..') assert_pathname_plus('/foo', '/', '../foo') assert_pathname_plus('foo/zap', 'foo/bar', '../zap') assert_pathname_plus('.', 'foo', '..') assert_pathname_plus('foo', '..', 'foo') # Auto clean assert_pathname_plus('foo', '..', '../foo') # Auto clean # Edge cases assert_pathname_plus('.', '.', '.') assert_pathname_plus('/', '/', '..') assert_pathname_plus('.', '..', '..') assert_pathname_plus('.', 'foo', '..') # Alias assert_equal('/foo/bar', Pathname.new('/foo') / Pathname.new('bar')) end # Any tests marked with '***' mean that this behavior is different than # the current implementation. It also means I disagree with the current # implementation. def test_clean # Standard stuff assert_equal('/a/b/c', Pathname.new('/a/b/c').cleanpath) assert_equal('b/c', Pathname.new('./b/c').cleanpath) assert_equal('a', Pathname.new('a/.').cleanpath) # *** assert_equal('a/c', Pathname.new('a/./c').cleanpath) assert_equal('a/b', Pathname.new('a/b/.').cleanpath) # *** assert_equal('.', Pathname.new('a/../.').cleanpath) # *** assert_equal('/a', Pathname.new('/a/b/..').cleanpath) assert_equal('/b', Pathname.new('/a/../b').cleanpath) assert_equal('d', Pathname.new('a/../../d').cleanpath) # *** # Edge cases assert_equal('', Pathname.new('').cleanpath) assert_equal('.', Pathname.new('.').cleanpath) assert_equal('..', Pathname.new('..').cleanpath) assert_equal('/', Pathname.new('/').cleanpath) assert_equal('/', Pathname.new('//').cleanpath) assert_non_destructive end def test_dirname_basic assert_respond_to(@abs_path, :dirname) assert_nothing_raised{ @abs_path.dirname } assert_kind_of(String, @abs_path.dirname) end def test_dirname assert_equal('/usr/local', @abs_path.dirname) assert_equal('/usr/local/bin', @abs_path.dirname(0)) assert_equal('/usr/local', @abs_path.dirname(1)) assert_equal('/usr', @abs_path.dirname(2)) assert_equal('/', @abs_path.dirname(3)) assert_equal('/', @abs_path.dirname(9)) end def test_dirname_expected_errors assert_raise(ArgumentError){ @abs_path.dirname(-1) } end def test_facade_io assert_respond_to(@abs_path, :foreach) assert_respond_to(@abs_path, :read) assert_respond_to(@abs_path, :readlines) assert_respond_to(@abs_path, :sysopen) end def test_facade_file File.methods(false).each{ |method| assert_respond_to(@abs_path, method.to_sym) } end def test_facade_dir Dir.methods(false).each{ |method| assert_respond_to(@abs_path, method.to_sym) } end def test_facade_fileutils methods = FileUtils.public_instance_methods methods -= File.methods(false) methods -= Dir.methods(false) methods.delete_if{ |m| m.to_s =~ /stream/ } methods.delete(:identical?) methods.delete(:sh) methods.delete(:ruby) methods.delete(:safe_ln) methods.delete(:split_all) methods.each{ |method| assert_respond_to(@abs_path, method.to_sym) } end def test_facade_find assert_respond_to(@abs_path, :find) assert_nothing_raised{ @abs_path.find{} } Pathname.new(Dir.pwd).find{ |f| Find.prune if f.match('CVS') assert_kind_of(Pathname, f) } end # Ensures that subclasses return the subclass as the class, not a hard # coded Pathname. # def test_subclasses assert_kind_of(MyPathname, @mypath) assert_kind_of(MyPathname, @mypath + MyPathname.new('foo')) assert_kind_of(MyPathname, @mypath.realpath) assert_kind_of(MyPathname, @mypath.children.first) end # Test to ensure that the pn{ } shortcut works # def test_kernel_method assert_respond_to(Kernel, :pn) assert_nothing_raised{ pn{'/foo'} } assert_kind_of(Pathname, pn{'/foo'}) assert_equal('/foo', pn{'/foo'}) end def test_pwd_singleton_method assert_respond_to(Pathname, :pwd) assert_kind_of(String, Pathname.pwd) assert_equal(@@pwd, Pathname.pwd) end test "String#to_path instance method is implemented" do string = "/usr/local/bin" assert_respond_to(string, :to_path) assert_nothing_raised{ string.to_path } assert_kind_of(Pathname, string.to_path) end def teardown @abs_path = nil @rel_path = nil @trl_path = nil @mul_path = nil @rul_path = nil @cur_path = nil @abs_path = nil @rel_path = nil @cur_path = nil @mypath = nil @abs_array.clear @rel_array.clear File.delete(@link_file2) if File.exist?(@link_file2) File.delete(@link_file) if File.exist?(@link_file) File.delete(@test_file) if File.exist?(@test_file) @link_file2 = nil @link_file = nil @test_file = nil end def self.shutdown @@pwd = nil end end pathname2-1.8.0/test/test_version.rb0000644000004100000410000000064412734555701017474 0ustar www-datawww-data######################################################################## # test_version.rb # # Universal test file that tests for the proper version number. ######################################################################## require 'pathname2' require 'test-unit' class TC_Pathname_Version < Test::Unit::TestCase test "version is set to expected value" do assert_equal('1.8.0', Pathname::VERSION) end end pathname2-1.8.0/MANIFEST0000644000004100000410000000211712734555701014572 0ustar www-datawww-data* CHANGES * MANIFEST * Rakefile * README * pathname2.gempsec * benchmarks/bench_all.rb * benchmarks/bench_plus.rb * certs/djberg96_pub.pem * examples/example_pathname.rb * lib/pathname2.rb * test/test_pathname.rb * test/test_version.rb * test/windows/test_append.rb * test/windows/test_aref.rb * test/windows/test_ascend.rb * test/windows/test_children.rb * test/windows/test_clean.rb * test/windows/test_clean_bang.rb * test/windows/test_constructor.rb * test/windows/test_descend.rb * test/windows/test_drive_number.rb * test/windows/test_each.rb * test/windows/test_facade.rb * test/windows/test_is_absolute.rb * test/windows/test_is_relative.rb * test/windows/test_is_root.rb * test/windows/test_is_unc.rb * test/windows/test_long_path.rb * test/windows/test_misc.rb * test/windows/test_parent.rb * test/windows/test_pstrip.rb * test/windows/test_pstrip_bang.rb * test/windows/test_realpath.rb * test/windows/test_relative_path_from.rb * test/windows/test_root.rb * test/windows/test_short_path.rb * test/windows/test_to_a.rb * test/windows/test_undecorate.rb * test/windows/test_undecorate_bang.rb pathname2-1.8.0/checksums.yaml.gz.sig0000444000004100000410000000040012734555701017501 0ustar www-datawww-data<ܿk\t-`̛rYУBNHCnILSYK歺:M Ip^:bx!6P?v Ȋ-hxlk݆h rake benchmark to run the pure Ruby benchmark. ##################################################################### require 'benchmark' require 'pathname2' require 'rbconfig' if RbConfig::CONFIG['host_os'] =~ /mingw|mswin/i path1 = Pathname.new("C:\\Program Files\\Windows NT") path2 = Pathname.new("Accessories") path3 = Pathname.new("C:\\Program Files\\..\\.\\Windows NT") else path1 = Pathname.new("/usr/local") path2 = Pathname.new("bin") path3 = Pathname.new("/usr/../local/./bin") path4 = Pathname.new("/dev/stdin") end MAX = 10000 Benchmark.bm(25) do |bench| bench.report("Pathname.new(path)"){ MAX.times{ Pathname.new("/usr/local/bin") } } bench.report("Pathname#+(Pathname)"){ MAX.times{ path1 + path2 } } bench.report("Pathname#+(String)"){ MAX.times{ path1 + path2 } } bench.report("Pathname#children"){ MAX.times{ path1.children } } bench.report("Pathname#pstrip"){ MAX.times{ path1.pstrip } } bench.report("Pathname#pstrip!"){ MAX.times{ path1.pstrip! } } bench.report("Pathname#to_a"){ MAX.times{ path1.to_a } } bench.report("Pathname#descend"){ MAX.times{ path1.descend{} } } bench.report("Pathname#ascend"){ MAX.times{ path1.ascend{} } } bench.report("Pathname#root"){ MAX.times{ path1.root } } bench.report("Pathname#root?"){ MAX.times{ path1.root? } } bench.report("Pathname#<=>"){ MAX.times{ path1 <=> path2 } } bench.report("Pathname#absolute?"){ MAX.times{ path1.absolute? } } bench.report("Pathname#relative?"){ MAX.times{ path1.relative? } } bench.report("Pathname#clean"){ MAX.times{ path3.clean } } bench.report("Pathname#clean!"){ MAX.times{ path3.clean! } } # Platform specific tests if RbConfig::CONFIG['host_os'] =~ /mingw|mswin/i bench.report("Pathname.new(file_url)"){ MAX.times{ Pathname.new("file:///C:/usr/local/bin") } } bench.report("Pathname#drive_number"){ MAX.times{ path1.drive_number } } bench.report("Pathname#unc?"){ MAX.times{ path1.unc? } } bench.report("Pathname#undecorate"){ MAX.times{ path1.undecorate } } bench.report("Pathname#undecorate!"){ MAX.times{ path1.undecorate! } } bench.report("Pathname#short_path"){ MAX.times{ path1.short_path } } bench.report("Pathname#long_path"){ MAX.times{ path1.long_path } } else bench.report("Pathname#realpath"){ MAX.times{ path4.realpath } } end end pathname2-1.8.0/certs/0000755000004100000410000000000012734555701014560 5ustar www-datawww-datapathname2-1.8.0/certs/djberg96_pub.pem0000644000004100000410000000234512734555701017551 0ustar www-datawww-data-----BEGIN CERTIFICATE----- MIIDcDCCAligAwIBAgIBATANBgkqhkiG9w0BAQUFADA/MREwDwYDVQQDDAhkamJl cmc5NjEVMBMGCgmSJomT8ixkARkWBWdtYWlsMRMwEQYKCZImiZPyLGQBGRYDY29t MB4XDTE1MDkwMjIwNDkxOFoXDTE2MDkwMTIwNDkxOFowPzERMA8GA1UEAwwIZGpi ZXJnOTYxFTATBgoJkiaJk/IsZAEZFgVnbWFpbDETMBEGCgmSJomT8ixkARkWA2Nv bTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAMyTkvXqRp6hLs9eoJOS Hmi8kRYbq9Vkf15/hMxJpotYMgJVHHWrmDcC5Dye2PbnXjTkKf266Zw0PtT9h+lI S3ts9HO+vaCFSMwFFZmnWJSpQ3CNw2RcHxjWkk9yF7imEM8Kz9ojhiDXzBetdV6M gr0lV/alUr7TNVBDngbXEfTWscyXh1qd7xZ4EcOdsDktCe5G45N/o3662tPQvJsi FOF0CM/KuBsa/HL1/eoEmF4B3EKIRfTHrQ3hu20Kv3RJ88QM4ec2+0dd97uX693O zv6981fyEg+aXLkxrkViM/tz2qR2ZE0jPhHTREPYeMEgptRkTmWSKAuLVWrJEfgl DtkCAwEAAaN3MHUwCQYDVR0TBAIwADALBgNVHQ8EBAMCBLAwHQYDVR0OBBYEFEwe nn6bfJADmuIDiMSOzedOrL+xMB0GA1UdEQQWMBSBEmRqYmVyZzk2QGdtYWlsLmNv bTAdBgNVHRIEFjAUgRJkamJlcmc5NkBnbWFpbC5jb20wDQYJKoZIhvcNAQEFBQAD ggEBAHmNOCWoDVD75zHFueY0viwGDVP1BNGFC+yXcb7u2GlK+nEMCORqzURbYPf7 tL+/hzmePIRz7i30UM//64GI1NLv9jl7nIwjhPpXpf7/lu2I9hOTsvwSumb5UiKC /sqBxI3sfj9pr79Wpv4MuikX1XPik7Ncb7NPsJPw06Lvyc3Hkg5X2XpPtLtS+Gr2 wKJnmzb5rIPS1cmsqv0M9LPWflzfwoZ/SpnmhagP+g05p8bRNKjZSA2iImM/GyYZ EJYzxdPOrx2n6NYR3Hk+vHP0U7UBSveI6+qx+ndQYaeyCn+GRX2PKS9h66YF/Q1V tGSHgAmcLlkdGgan182qsE/4kKM= -----END CERTIFICATE----- pathname2-1.8.0/pathname2.gemspec0000644000004100000410000000263612734555701016673 0ustar www-datawww-datarequire 'rubygems' Gem::Specification.new do |spec| spec.name = 'pathname2' spec.version = '1.8.0' spec.author = 'Daniel J. Berger' spec.license = 'Apache 2.0' spec.email = 'djberg96@gmail.com' spec.homepage = 'https://github.com/djberg96/pathname2' spec.summary = 'An alternate implementation of the Pathname class' spec.files = Dir['**/*'].reject{ |f| f.include?('git') } spec.cert_chain = ['certs/djberg96_pub.pem'] spec.extra_rdoc_files = ['README', 'CHANGES', 'MANIFEST'] spec.add_dependency('facade') spec.add_development_dependency('test-unit') spec.add_development_dependency('rake') if File::ALT_SEPARATOR spec.add_dependency('ffi') spec.test_files = FileList['test/windows/*.rb', 'test/test_version.rb'] spec.platform = Gem::Platform.new(['universal', 'mingw32']) else spec.test_files = FileList['test/test_pathname.rb', 'test/test_version.rb'] end spec.description = <<-EOF The pathname2 library provides an implementation of the Pathname class different from the one that ships as part of the Ruby standard library. It is a subclass of String, though several methods have been overridden to better fit a path context. In addition, it supports file URL's as paths, provides additional methods for Windows paths, and handles UNC paths on Windows properly. See the README file for more details. EOF end pathname2-1.8.0/metadata.gz.sig0000444000004100000410000000040012734555701016333 0ustar www-datawww-data2W?8)ĂrZl 0igd:O;ʄ3``EnbteU{Ҳ `0ܥL)*+g$ߵKʴ{gqS?¬JĬ hƋݴ y?@S **jAC-cw*4<g-=Q@QGC%3<Ț*=xzx:f<4]%pathname2-1.8.0/CHANGES0000644000004100000410000001470112734555701014436 0ustar www-datawww-data== 1.8.0 - 19-Jun-2016 * Changed license to Apache 2.0. * Some cleanup and updates to the Rakefile and benchmarks. * Refactored some realpath tests so they're not touching system files like /dev/stdin any more. Thanks go to Michael R. Crusoe for pointing out the potential pitfalls of doing that. == 1.7.4 - 7-Sep-2015 * This gem is now signed. * Rakefile now assumes Rubygems 2.x for some tasks. == 1.7.3 - 24-Apr-2014 * The basename and dirname methods now return Pathname objects. == 1.7.2 - 23-Apr-2014 * The join and expand_path methods now return Pathname objects. == 1.7.1 - 28-Mar-2014 * Updated gemspec for Windows vs Unix. * Updated README and MANIFEST. == 1.7.0 - 28-Mar-2014 * Windows now uses FFI internally instead of win32-api. * Added a custom pretty_print method for the pp library. * Reorganized the test suite for Windows, and added many more test tasks to the Rakefile. == 1.6.5 - 19-Sep-2011 * Added the String#to_path instance method. This returns a Pathname object. * The architecture for the Windows gem is now "universal", and some gemspec dependencies were simplified. == 1.6.4 - 20-Jan-2011 * Explicitly remove the Pathname const if it is already defined in order to avoid a superclass mismatch error. This library assumes that if you require pathname2, you want my version of the Pathname class. * Updated URI handling for Ruby 1.9.x. * Added the Pathname() method, a synonym for Pathname.new. * Some Rakefile and gemspec tweaks. * Some updates to the test suite, including some specifically for Windows 7. == 1.6.3 - 2-Oct-2009 * Updated Windows platform handling code to include mingw and cygwin. * Added the :gem rake task. * Minor gemspec updates. * Some minor test suite updates. == 1.6.2 - 4-Aug-2009 * Now compatible with Ruby 1.9.x. * License changed to Artistic 2.0. * Added the Pathname.pwd method as a synonym for Pathname.new(Dir.pwd). * Modified Pathname#dirname so that you can specify a level that indicates how many levels up you want to retrieve. For example, if your path was '/usr/local/bin', then path.dirname(2) would return '/usr'. * Now compatible with Ruby 1.9.x. * Bumped required version of the facade library to 1.0.4. == 1.6.1 - 8-Nov-2008 * Added the Pathname#[] method, which accepts an index, an index plus a length, or a range, and returns appropriate the path element(s). * Refactoring the platform checking in the test suite to use rbconfig instead of RUBY_PLATFORM. * More inline documentation examples. == 1.6.0 - 13-July-2008 * The facade for ftools (and ftools itself) has been removed. The ftools library is deprecated in favor of FileUtils. * PathnameError is now Pathname::Error. * Bug fix for Pathname#relative_path_from for MS Windows. Thanks go to an anonymous user for the spot. * Fixed a bug where frozen strings would raise an error on MS Windows. * The code is now -w clean. * Removed the C version as part of the release because it was just too difficult to maintain both versions. The C code remains in CVS, however. * Changed platform checking to use rbconfig instead of RUBY_PLATFORM to avoid potential issues with other Ruby implementation. == 1.5.2 - 9-Mar-2007 * Bug fix for the Pathname#realpath method where it was not handling recursive symlinks. The C version was also fixed, but it only affected platforms that don't have the realpath() function. * Added a test for recursive symlinks (for Solaris, anyway). * Updated the docs for Pathname#realpath. * Minor speed enhancements for the C version and the elimination of one (potential) segfault. * Added a 'Future Plans' section to the README. * Added a Rakefile. You can now build, clean, and test and install (both the pure Ruby and C versions). == 1.5.1 - 28-Aug-2006 * Added the Kernel#pn method as a shortcut for Pathname.new. * The Pathname#readlink now properly handles symbolic links. The 'fix' from 1.4.4 did not work. * The C extension uses your system's realpath() function for the Pathname#readlink method if it has one. * Added the '/' alias for '+'. So, p1 / p2 is the same as p1 + p2. * The windows-pr package is now required on MS Windows. == 1.5.0 - 17-Apr-2006 * Better subclass handling, in that some methods that previously returned hardcoded Pathname.new now return self.class.new. * File URL's are now handled on Unix as well (using the 'uri' package). * Some comment changes/clarifications. * Added the PathnameError class to the pure Ruby version. == 1.4.4 - 23-Mar-2006 * If the path is a symbolic link the Pathname#realpath method now returns the absolute path of that link, i.e. the result of File.readlink (as a Pathname object). == 1.4.3 - 3-Mar-2006 * Added the Pathname#realpath method. == 1.4.2 - 22-Feb-2006 * Fixed the Pathname#relative_path_from method for Windows. This really only affected edge cases that you probably never saw anyway. * Added corresponding tests for Windows. == 1.4.1 - 18-Feb-2006 * Added the Pathname#parent method. * Added the Pathname#relative_path_from method. * Bug fix for Pathname#pstrip on *nix. * Corresponding test suite additions. == 1.4.0 - 19-Dec-2005 * Added destructive and non-destructive methods for some methods - pstrip, pstrip!, undecorate, undecorate!, clean and clean!. * Added a C extension version of this package. You can use the C version instead of the pure Ruby version instead. See the README for more details. * Fixed bug in the root method where the result wasn't guaranteed to be a Pathname class. * Fixed bugs in Windows version where the receiver was inadvertantly modified in some cases, and added tests to check for this in the future. * Modified the Dir.glob facade so that it (temporarily) changes to the path directory, globs on that path, then returns to the original directory. * Added the bench_pathname.rb script to let you benchmark all Pathname methods. == 1.3.1 - 21-Nov-2005 * Added the Pathname#children method. * Added tests for the Pathname#children method. == 1.3.0 - 28-Oct-2005 * Added the short_path and long_path methods for MS Windows. * Optimization for the '+' method on Unix. * Added some examples under the 'examples' directory. * More tests added and some minor changes to the test suite in general. == 1.2.1 - 1-Sep-2005 * Bug fix for the ascend and descend methods wrt Windows and UNC paths. * More tests added for ascend and descend methods. == 1.2.0 - 29-Aug-2005 * Added the 'ascend' and 'descend' methods. * Added corresponding test suite additions. == 1.1.0 - 13-Jul-2005 * Added the 'find' facade. == 1.0.0 - 11-Jun-2005 * Initial release