ptools 1.2.2-universal-mingw32

Sign up to get free protection for your applications and to get access to all the features.
data/lib/ptools.rb ADDED
@@ -0,0 +1,429 @@
1
+ require 'rbconfig'
2
+ require 'win32/file' if File::ALT_SEPARATOR
3
+
4
+ class File
5
+ # The version of the ptools library.
6
+ PTOOLS_VERSION = '1.2.2'
7
+
8
+ # :stopdoc:
9
+
10
+ # The WIN32EXTS string is used as part of a Dir[] call in certain methods.
11
+ if File::ALT_SEPARATOR
12
+ MSWINDOWS = true
13
+ if ENV['PATHEXT']
14
+ WIN32EXTS = ('.{' + ENV['PATHEXT'].tr(';', ',').tr('.','') + '}').downcase
15
+ else
16
+ WIN32EXTS = '.{exe,com,bat}'
17
+ end
18
+ else
19
+ MSWINDOWS = false
20
+ end
21
+
22
+ IMAGE_EXT = %w[.bmp .gif .jpg .jpeg .png]
23
+
24
+ # :startdoc:
25
+
26
+ # Returns whether or not the file is an image. Only JPEG, PNG, BMP and
27
+ # GIF are checked against.
28
+ #
29
+ # This method does some simple read and extension checks. For a version
30
+ # that is more robust, but which depends on a 3rd party C library (and is
31
+ # difficult to build on MS Windows), see the 'filemagic' library, available
32
+ # on the RAA.
33
+ #
34
+ # Examples:
35
+ #
36
+ # File.image?('somefile.jpg') # => true
37
+ # File.image?('somefile.txt') # => true
38
+ #--
39
+ # The approach I used here is based on information found at
40
+ # http://en.wikipedia.org/wiki/Magic_number_(programming)
41
+ #
42
+ def self.image?(file)
43
+ bool = IMAGE_EXT.include?(File.extname(file).downcase) # Match ext
44
+ bool = bmp?(file) || jpg?(file) || png?(file) || gif?(file) # Check data
45
+ bool
46
+ end
47
+
48
+ # Returns the name of the null device (aka bitbucket) on your platform.
49
+ #
50
+ # Examples:
51
+ #
52
+ # # On Linux
53
+ # File.null # => '/dev/null'
54
+ #
55
+ # # On MS Windows
56
+ # File.null # => 'NUL'
57
+ #--
58
+ # The values I used here are based on information from
59
+ # http://en.wikipedia.org/wiki//dev/null
60
+ #
61
+ def self.null
62
+ case RbConfig::CONFIG['host_os']
63
+ when /mswin|win32|msdos|cygwin|mingw|windows/i
64
+ 'NUL'
65
+ when /amiga/i
66
+ 'NIL:'
67
+ when /openvms/i
68
+ 'NL:'
69
+ else
70
+ '/dev/null'
71
+ end
72
+ end
73
+
74
+ class << self
75
+ alias null_device null
76
+ end
77
+
78
+ # Returns whether or not +file+ is a binary file. Note that this is
79
+ # not guaranteed to be 100% accurate. It performs a "best guess" based
80
+ # on a simple test of the first +File.blksize+ characters.
81
+ #
82
+ # Example:
83
+ #
84
+ # File.binary?('somefile.exe') # => true
85
+ # File.binary?('somefile.txt') # => false
86
+ #--
87
+ # Based on code originally provided by Ryan Davis (which, in turn, is
88
+ # based on Perl's -B switch).
89
+ #
90
+ def self.binary?(file)
91
+ s = (File.read(file, File.stat(file).blksize) || "").split(//)
92
+ ((s.size - s.grep(" ".."~").size) / s.size.to_f) > 0.30
93
+ end
94
+
95
+ # Looks for the first occurrence of +program+ within +path+.
96
+ #
97
+ # On Windows, it looks for executables ending with the suffixes defined
98
+ # in your PATHEXT environment variable, or '.exe', '.bat' and '.com' if
99
+ # that isn't defined, which you may optionally include in +program+.
100
+ #
101
+ # Returns nil if not found.
102
+ #
103
+ # Examples:
104
+ #
105
+ # File.which('ruby') # => '/usr/local/bin/ruby'
106
+ # File.which('foo') # => nil
107
+ #
108
+ def self.which(program, path=ENV['PATH'])
109
+ if path.nil? || path.empty?
110
+ raise ArgumentError, "path cannot be empty"
111
+ end
112
+
113
+ # Bail out early if an absolute path is provided.
114
+ if program =~ /^\/|^[a-z]:[\\\/]/i
115
+ program += WIN32EXTS if MSWINDOWS && File.extname(program).empty?
116
+ found = Dir[program].first
117
+ if found && File.executable?(found) && !File.directory?(found)
118
+ return found
119
+ else
120
+ return nil
121
+ end
122
+ end
123
+
124
+ # Iterate over each path glob the dir + program.
125
+ path.split(File::PATH_SEPARATOR).each{ |dir|
126
+ next unless File.exists?(dir) # In case of bogus second argument
127
+ file = File.join(dir, program)
128
+
129
+ # Dir[] doesn't handle backslashes properly, so convert them. Also, if
130
+ # the program name doesn't have an extension, try them all.
131
+ if MSWINDOWS
132
+ file = file.tr("\\", "/")
133
+ file += WIN32EXTS if File.extname(program).empty?
134
+ end
135
+
136
+ found = Dir[file].first
137
+
138
+ # Convert all forward slashes to backslashes if supported
139
+ if found && File.executable?(found) && !File.directory?(found)
140
+ found.tr!(File::SEPARATOR, File::ALT_SEPARATOR) if File::ALT_SEPARATOR
141
+ return found
142
+ end
143
+ }
144
+
145
+ nil
146
+ end
147
+
148
+ # Returns an array of each +program+ within +path+, or nil if it cannot
149
+ # be found.
150
+ #
151
+ # On Windows, it looks for executables ending with the suffixes defined
152
+ # in your PATHEXT environment variable, or '.exe', '.bat' and '.com' if
153
+ # that isn't defined, which you may optionally include in +program+.
154
+ #
155
+ # Examples:
156
+ #
157
+ # File.whereis('ruby') # => ['/usr/bin/ruby', '/usr/local/bin/ruby']
158
+ # File.whereis('foo') # => nil
159
+ #
160
+ def self.whereis(program, path=ENV['PATH'])
161
+ if path.nil? || path.empty?
162
+ raise ArgumentError, "path cannot be empty"
163
+ end
164
+
165
+ paths = []
166
+
167
+ # Bail out early if an absolute path is provided.
168
+ if program =~ /^\/|^[a-z]:[\\\/]/i
169
+ program += WIN32EXTS if MSWINDOWS && File.extname(program).empty?
170
+ program = program.tr("\\", '/') if MSWINDOWS
171
+ found = Dir[program]
172
+ if found[0] && File.executable?(found[0]) && !File.directory?(found[0])
173
+ if File::ALT_SEPARATOR
174
+ return found.map{ |f| f.tr('/', "\\") }
175
+ else
176
+ return found
177
+ end
178
+ else
179
+ return nil
180
+ end
181
+ end
182
+
183
+ # Iterate over each path glob the dir + program.
184
+ path.split(File::PATH_SEPARATOR).each{ |dir|
185
+ next unless File.exists?(dir) # In case of bogus second argument
186
+ file = File.join(dir, program)
187
+
188
+ # Dir[] doesn't handle backslashes properly, so convert them. Also, if
189
+ # the program name doesn't have an extension, try them all.
190
+ if MSWINDOWS
191
+ file = file.tr("\\", "/")
192
+ file += WIN32EXTS if File.extname(program).empty?
193
+ end
194
+
195
+ found = Dir[file].first
196
+
197
+ # Convert all forward slashes to backslashes if supported
198
+ if found && File.executable?(found) && !File.directory?(found)
199
+ found.tr!(File::SEPARATOR, File::ALT_SEPARATOR) if File::ALT_SEPARATOR
200
+ paths << found
201
+ end
202
+ }
203
+
204
+ paths.empty? ? nil : paths.uniq
205
+ end
206
+
207
+ # In block form, yields the first +num_lines+ from +filename+. In non-block
208
+ # form, returns an Array of +num_lines+
209
+ #
210
+ # Examples:
211
+ #
212
+ # # Return an array
213
+ # File.head('somefile.txt') # => ['This is line1', 'This is line2', ...]
214
+ #
215
+ # # Use a block
216
+ # File.head('somefile.txt'){ |line| puts line }
217
+ #
218
+ def self.head(filename, num_lines=10)
219
+ a = []
220
+
221
+ IO.foreach(filename){ |line|
222
+ break if num_lines <= 0
223
+ num_lines -= 1
224
+ if block_given?
225
+ yield line
226
+ else
227
+ a << line
228
+ end
229
+ }
230
+
231
+ return a.empty? ? nil : a # Return nil in block form
232
+ end
233
+
234
+ # In block form, yields line +from+ up to line +to+. In non-block form
235
+ # returns an Array of lines from +from+ to +to+.
236
+ #
237
+ def self.middle(filename, from=10, to=20)
238
+ if block_given?
239
+ IO.readlines(filename)[from-1..to-1].each{ |line| yield line }
240
+ else
241
+ IO.readlines(filename)[from-1..to-1]
242
+ end
243
+ end
244
+
245
+ # In block form, yields the last +num_lines+ of file +filename+.
246
+ # In non-block form, it returns the lines as an array.
247
+ #
248
+ # Note that this method slurps the entire file, so I don't recommend it
249
+ # for very large files. Also note that 'tail -f' functionality is not
250
+ # present. See the 'file-tail' library for that.
251
+ #
252
+ # Example:
253
+ #
254
+ # File.tail('somefile.txt') # => ['This is line7', 'This is line8', ...]
255
+ #
256
+ def self.tail(filename, num_lines=10)
257
+ if block_given?
258
+ IO.readlines(filename).reverse[0..num_lines-1].reverse.each{ |line|
259
+ yield line
260
+ }
261
+ else
262
+ IO.readlines(filename).reverse[0..num_lines-1].reverse
263
+ end
264
+ end
265
+
266
+ # Converts a text file from one OS platform format to another, ala
267
+ # 'dos2unix'. The possible values for +platform+ include:
268
+ #
269
+ # * MS Windows -> dos, windows, win32, mswin
270
+ # * Unix/BSD -> unix, linux, bsd
271
+ # * Mac -> mac, macintosh, apple, osx
272
+ #
273
+ # Note that this method is only valid for an ftype of "file". Otherwise a
274
+ # TypeError will be raised. If an invalid format value is received, an
275
+ # ArgumentError is raised.
276
+ #
277
+ def self.nl_convert(old_file, new_file = old_file, platform = 'dos')
278
+ unless File::Stat.new(old_file).file?
279
+ raise ArgumentError, 'Only valid for plain text files'
280
+ end
281
+
282
+ case platform
283
+ when /dos|windows|win32|mswin|cygwin|mingw/i
284
+ format = "\cM\cJ"
285
+ when /unix|linux|bsd/i
286
+ format = "\cJ"
287
+ when /mac|apple|macintosh|osx/i
288
+ format = "\cM"
289
+ else
290
+ raise ArgumentError, "Invalid platform string"
291
+ end
292
+
293
+ orig = $\ # AKA $OUTPUT_RECORD_SEPARATOR
294
+ $\ = format
295
+
296
+ if old_file == new_file
297
+ require 'fileutils'
298
+ require 'tempfile'
299
+
300
+ begin
301
+ temp_name = Time.new.strftime("%Y%m%d%H%M%S")
302
+ tf = Tempfile.new('ruby_temp_' + temp_name)
303
+ tf.open
304
+
305
+ IO.foreach(old_file){ |line|
306
+ line.chomp!
307
+ tf.print line
308
+ }
309
+ ensure
310
+ tf.close if tf && !tf.closed?
311
+ end
312
+
313
+ File.delete(old_file)
314
+ FileUtils.cp(tf.path, old_file)
315
+ else
316
+ begin
317
+ nf = File.new(new_file, 'w')
318
+ IO.foreach(old_file){ |line|
319
+ line.chomp!
320
+ nf.print line
321
+ }
322
+ ensure
323
+ nf.close if nf && !nf.closed?
324
+ end
325
+ end
326
+
327
+ $\ = orig
328
+ self
329
+ end
330
+
331
+ # Changes the access and modification time if present, or creates a 0
332
+ # byte file +filename+ if it doesn't already exist.
333
+ #
334
+ def self.touch(filename)
335
+ if File.exists?(filename)
336
+ time = Time.now
337
+ File.utime(time, time, filename)
338
+ else
339
+ File.open(filename, 'w'){}
340
+ end
341
+ self
342
+ end
343
+
344
+ # With no arguments, returns a four element array consisting of the number
345
+ # of bytes, characters, words and lines in filename, respectively.
346
+ #
347
+ # Valid options are 'bytes', 'characters' (or just 'chars'), 'words' and
348
+ # 'lines'.
349
+ #
350
+ def self.wc(filename, option='all')
351
+ option.downcase!
352
+ valid = %w/all bytes characters chars lines words/
353
+
354
+ unless valid.include?(option)
355
+ raise ArgumentError, "Invalid option: '#{option}'"
356
+ end
357
+
358
+ n = 0
359
+
360
+ if option == 'lines'
361
+ IO.foreach(filename){ n += 1 }
362
+ return n
363
+ elsif option == 'bytes'
364
+ File.open(filename){ |f|
365
+ f.each_byte{ n += 1 }
366
+ }
367
+ return n
368
+ elsif option == 'characters' || option == 'chars'
369
+ File.open(filename){ |f|
370
+ while f.getc
371
+ n += 1
372
+ end
373
+ }
374
+ return n
375
+ elsif option == 'words'
376
+ IO.foreach(filename){ |line|
377
+ n += line.split.length
378
+ }
379
+ return n
380
+ else
381
+ bytes,chars,lines,words = 0,0,0,0
382
+ IO.foreach(filename){ |line|
383
+ lines += 1
384
+ words += line.split.length
385
+ chars += line.split('').length
386
+ }
387
+ File.open(filename){ |f|
388
+ while f.getc
389
+ bytes += 1
390
+ end
391
+ }
392
+ return [bytes,chars,words,lines]
393
+ end
394
+ end
395
+
396
+ # Already provided by win32-file on MS Windows
397
+ unless respond_to?(:sparse?)
398
+ # Returns whether or not +file+ is a sparse file.
399
+ #
400
+ # A sparse file is a any file where its size is greater than the number
401
+ # of 512k blocks it consumes, i.e. its apparent and actual file size is
402
+ # not the same.
403
+ #
404
+ # See http://en.wikipedia.org/wiki/Sparse_file for more information.
405
+ #
406
+ def self.sparse?(file)
407
+ stats = File.stat(file)
408
+ stats.size > stats.blocks * 512
409
+ end
410
+ end
411
+
412
+ private
413
+
414
+ def self.bmp?(file)
415
+ IO.read(file, 3) == "BM6"
416
+ end
417
+
418
+ def self.jpg?(file)
419
+ IO.read(file, 10) == "\377\330\377\340\000\020JFIF"
420
+ end
421
+
422
+ def self.png?(file)
423
+ IO.read(file, 4) == "\211PNG"
424
+ end
425
+
426
+ def self.gif?(file)
427
+ ['GIF89a', 'GIF97a'].include?(IO.read(file, 6))
428
+ end
429
+ end
data/ptools.gemspec ADDED
@@ -0,0 +1,30 @@
1
+ require 'rubygems'
2
+ require 'rbconfig'
3
+
4
+ Gem::Specification.new do |gem|
5
+ gem.name = 'ptools'
6
+ gem.version = '1.2.2'
7
+ gem.license = 'Artistic 2.0'
8
+ gem.author = 'Daniel J. Berger'
9
+ gem.email = 'djberg96@gmail.com'
10
+ gem.homepage = 'http://www.rubyforge.org/projects/shards'
11
+ gem.summary = 'Extra methods for the File class'
12
+ gem.test_files = Dir['test/test*']
13
+ gem.files = Dir['**/*'] << '.gemtest'
14
+
15
+ gem.rubyforge_project = 'shards'
16
+ gem.extra_rdoc_files = ['README', 'CHANGES', 'MANIFEST']
17
+
18
+ gem.description = <<-EOF
19
+ The ptools (power tools) library provides several handy methods to
20
+ Ruby's core File class, such as File.which for finding executables,
21
+ File.null to return the null device on your platform, and so on.
22
+ EOF
23
+
24
+ gem.add_development_dependency('test-unit', '>= 2.4.0')
25
+
26
+ if File::ALT_SEPARATOR
27
+ gem.platform = Gem::Platform.new(['universal', 'mingw32'])
28
+ gem.add_dependency('win32-file', '>= 0.5.4')
29
+ end
30
+ end
@@ -0,0 +1,47 @@
1
+ #####################################################################
2
+ # test_binary.rb
3
+ #
4
+ # Test case for the File.binary? method. You should run this test
5
+ # via the 'rake test_binary' task.
6
+ #####################################################################
7
+ require 'rubygems'
8
+ require 'test-unit'
9
+ require 'ptools'
10
+
11
+ class TC_Ptools_Binary < Test::Unit::TestCase
12
+ def self.startup
13
+ @@txt_file = 'test_binary.txt'
14
+
15
+ if File::ALT_SEPARATOR
16
+ @@bin_file = File.join(ENV['windir'], 'notepad.exe')
17
+ else
18
+ @@bin_file = '/bin/ls'
19
+ end
20
+
21
+ Dir.chdir('test') if File.exists?('test')
22
+
23
+ File.open(@@txt_file, 'w'){ |fh| 10.times{ |n| fh.puts "line #{n}" } }
24
+ end
25
+
26
+ test "File.binary? basic functionality" do
27
+ assert_respond_to(File, :binary?)
28
+ assert_nothing_raised{ File.binary?(@@txt_file) }
29
+ end
30
+
31
+ test "File.binary? returns expected results" do
32
+ assert_false(File.binary?(@@txt_file))
33
+ assert_true(File.binary?(@@bin_file))
34
+ end
35
+
36
+ test "File.binary? raises an error if the file cannot be found" do
37
+ assert_raise_kind_of(SystemCallError){ File.binary?('bogus') }
38
+ end
39
+
40
+ test "File.binary? only accepts one argument" do
41
+ assert_raise_kind_of(ArgumentError){ File.binary?(@@txt_file, @@bin_file) }
42
+ end
43
+
44
+ def self.shutdown
45
+ File.delete(@@txt_file) if File.exists?(@@txt_file)
46
+ end
47
+ end
@@ -0,0 +1,38 @@
1
+ #####################################################################
2
+ # test_constants.rb
3
+ #
4
+ # Tests the constants that have been defined for our package. This
5
+ # test case should be run via the 'rake test_constants' task.
6
+ #####################################################################
7
+ require 'rubygems'
8
+ require 'test-unit'
9
+ require 'rbconfig'
10
+ require 'ptools'
11
+
12
+ class TC_Ptools_Constants < Test::Unit::TestCase
13
+ def self.startup
14
+ @@windows = File::ALT_SEPARATOR
15
+ end
16
+
17
+ test "PTOOLS_VERSION constant is set to expected value" do
18
+ assert_equal('1.2.2', File::PTOOLS_VERSION)
19
+ end
20
+
21
+ test "IMAGE_EXT constant is set to array of values" do
22
+ assert_equal(%w[.bmp .gif .jpeg .jpg .png], File::IMAGE_EXT.sort)
23
+ end
24
+
25
+ test "WINDOWS constant is defined on MS Windows" do
26
+ omit_unless(@@windows, "Skipping on Unix systems")
27
+ assert_not_nil(File::MSWINDOWS)
28
+ end
29
+
30
+ test "WIN32EXTS constant is defiend on MS Windows" do
31
+ omit_unless(@@windows, "Skipping on Unix systems")
32
+ assert_not_nil(File::WIN32EXTS)
33
+ end
34
+
35
+ def self.shutdown
36
+ @@windows = nil
37
+ end
38
+ end
data/test/test_head.rb ADDED
@@ -0,0 +1,51 @@
1
+ ######################################################################
2
+ # test_head.rb
3
+ #
4
+ # Test case for the File.head method. This test should be run via
5
+ # the 'rake test_head' task.
6
+ ######################################################################
7
+ require 'rubygems'
8
+ gem 'test-unit'
9
+
10
+ require 'test/unit'
11
+ require 'ptools'
12
+
13
+ class TC_FileHead < Test::Unit::TestCase
14
+ def self.startup
15
+ Dir.chdir('test') if File.exists?('test')
16
+ File.open('test_file1.txt', 'w'){ |fh| 25.times{ |n| fh.puts "line#{n+1}" } }
17
+ end
18
+
19
+ def setup
20
+ @test_file = 'test_file1.txt'
21
+ @expected_head1 = ["line1\n","line2\n","line3\n","line4\n","line5\n"]
22
+ @expected_head1.push("line6\n","line7\n","line8\n","line9\n","line10\n")
23
+ @expected_head2 = ["line1\n","line2\n","line3\n","line4\n","line5\n"]
24
+ end
25
+
26
+ def test_head_basic
27
+ assert_respond_to(File, :head)
28
+ assert_nothing_raised{ File.head(@test_file) }
29
+ assert_nothing_raised{ File.head(@test_file, 5) }
30
+ assert_nothing_raised{ File.head(@test_file){} }
31
+ end
32
+
33
+ def test_head_expected_results
34
+ assert_kind_of(Array, File.head(@test_file))
35
+ assert_equal(@expected_head1, File.head(@test_file))
36
+ assert_equal(@expected_head2, File.head(@test_file, 5))
37
+ end
38
+
39
+ def test_head_expected_errors
40
+ assert_raises(ArgumentError){ File.head(@test_file, 5, "foo") }
41
+ assert_raises(Errno::ENOENT){ File.head("bogus") }
42
+ end
43
+
44
+ def teardown
45
+ @test_file = nil
46
+ end
47
+
48
+ def self.shutdown
49
+ File.delete('test_file1.txt') if File.exists?('test_file1.txt')
50
+ end
51
+ end
@@ -0,0 +1,43 @@
1
+ #####################################################################
2
+ # test_image.rb
3
+ #
4
+ # Test case for the File.image? method. You should run this test
5
+ # via the 'rake test_image' task.
6
+ #####################################################################
7
+ require 'rubygems'
8
+ gem 'test-unit'
9
+
10
+ require 'test/unit'
11
+ require 'ptools'
12
+
13
+ class TC_Ptools_Image < Test::Unit::TestCase
14
+ def self.startup
15
+ Dir.chdir('test') if File.exists?('test')
16
+ File.open('test_file1.txt', 'w'){ |fh| 25.times{ |n| fh.puts "line#{n+1}" } }
17
+ end
18
+
19
+ def setup
20
+ @text_file = 'test_file1.txt'
21
+ end
22
+
23
+ def test_image_basic
24
+ assert_respond_to(File, :image?)
25
+ assert_nothing_raised{ File.image?(@text_file) }
26
+ end
27
+
28
+ def test_image_expected_results
29
+ assert_equal(false, File.image?(@text_file))
30
+ end
31
+
32
+ def test_image_expected_errors
33
+ assert_raises(Errno::ENOENT, ArgumentError){ File.image?('bogus') }
34
+ end
35
+
36
+ def teardown
37
+ @text_file = nil
38
+ end
39
+
40
+ def self.shutdown
41
+ File.delete('test_file1.txt') if File.exists?('test_file1.txt')
42
+ end
43
+ end
@@ -0,0 +1,52 @@
1
+ #####################################################################
2
+ # test_is_sparse.rb
3
+ #
4
+ # Test case for the File.sparse? method. You should run this test
5
+ # via the 'rake test:is_sparse' task.
6
+ #####################################################################
7
+ require 'rubygems'
8
+ gem 'test-unit'
9
+
10
+ require 'test/unit'
11
+ require 'ptools'
12
+
13
+ class TC_IsSparse < Test::Unit::TestCase
14
+ def self.startup
15
+ Dir.chdir("test") if File.exists?("test")
16
+ @@win = RbConfig::CONFIG['host_os'] =~ /windows|mswin|dos|cygwin|mingw/i
17
+ @@osx = RbConfig::CONFIG['host_os'] =~ /darwin|osx/i
18
+ @@sun = RbConfig::CONFIG['host_os'] =~ /sunos|solaris/i
19
+ end
20
+
21
+ def setup
22
+ @sparse_file = @@sun ? '/var/adm/lastlog' : '/var/log/lastlog'
23
+ @non_sparse_file = File.expand_path(File.basename(__FILE__))
24
+ end
25
+
26
+ test "is_sparse basic functionality" do
27
+ omit_if(@@win, "File.sparse? tests skipped on MS Windows")
28
+ omit_if(@@osx, "File.sparse? tests skipped on OS X")
29
+
30
+ assert_respond_to(File, :sparse?)
31
+ assert_nothing_raised{ File.sparse?(@sparse_file) }
32
+ assert_boolean(File.sparse?(@sparse_file))
33
+ end
34
+
35
+ test "is_sparse returns the expected results" do
36
+ omit_if(@@win, "File.sparse? tests skipped on MS Windows")
37
+ omit_if(@@osx, "File.sparse? tests skipped on OS X")
38
+
39
+ assert_true(File.sparse?(@sparse_file))
40
+ assert_false(File.sparse?(@non_sparse_file))
41
+ end
42
+
43
+ test "is_sparse only accepts one argument" do
44
+ omit_if(@@win, "File.sparse? tests skipped on MS Windows")
45
+ assert_raise(ArgumentError){ File.sparse?(@sparse_file, @sparse_file) }
46
+ end
47
+
48
+ def teardown
49
+ @sparse_file = nil
50
+ @non_sparse_file = nil
51
+ end
52
+ end