PageRenderTime 191ms CodeModel.GetById 36ms RepoModel.GetById 3ms app.codeStats 0ms

/tools/Rake/lib/ruby/gems/1.8/gems/rubyzip-0.9.4/test/ziptest.rb

https://github.com/ncgonz/Giles
Ruby | 1620 lines | 1385 code | 207 blank | 28 comment | 57 complexity | 44f6edd65222d4b689a6afce8edb30c2 MD5 | raw file
Possible License(s): BSD-2-Clause, Apache-2.0, MPL-2.0-no-copyleft-exception, BSD-3-Clause, GPL-2.0
  1. #!/usr/bin/env ruby
  2. $VERBOSE = true
  3. $: << "../lib"
  4. require 'test/unit'
  5. require 'fileutils'
  6. require 'zip/zip'
  7. require 'gentestfiles'
  8. include Zip
  9. class ZipEntryTest < Test::Unit::TestCase
  10. TEST_ZIPFILE = "someZipFile.zip"
  11. TEST_COMMENT = "a comment"
  12. TEST_COMPRESSED_SIZE = 1234
  13. TEST_CRC = 325324
  14. TEST_EXTRA = "Some data here"
  15. TEST_COMPRESSIONMETHOD = ZipEntry::DEFLATED
  16. TEST_NAME = "entry name"
  17. TEST_SIZE = 8432
  18. TEST_ISDIRECTORY = false
  19. def test_constructorAndGetters
  20. entry = ZipEntry.new(TEST_ZIPFILE,
  21. TEST_NAME,
  22. TEST_COMMENT,
  23. TEST_EXTRA,
  24. TEST_COMPRESSED_SIZE,
  25. TEST_CRC,
  26. TEST_COMPRESSIONMETHOD,
  27. TEST_SIZE)
  28. assert_equal(TEST_COMMENT, entry.comment)
  29. assert_equal(TEST_COMPRESSED_SIZE, entry.compressed_size)
  30. assert_equal(TEST_CRC, entry.crc)
  31. assert_instance_of(Zip::ZipExtraField, entry.extra)
  32. assert_equal(TEST_COMPRESSIONMETHOD, entry.compression_method)
  33. assert_equal(TEST_NAME, entry.name)
  34. assert_equal(TEST_SIZE, entry.size)
  35. assert_equal(TEST_ISDIRECTORY, entry.is_directory)
  36. end
  37. def test_is_directoryAndIsFile
  38. assert(ZipEntry.new(TEST_ZIPFILE, "hello").file?)
  39. assert(! ZipEntry.new(TEST_ZIPFILE, "hello").directory?)
  40. assert(ZipEntry.new(TEST_ZIPFILE, "dir/hello").file?)
  41. assert(! ZipEntry.new(TEST_ZIPFILE, "dir/hello").directory?)
  42. assert(ZipEntry.new(TEST_ZIPFILE, "hello/").directory?)
  43. assert(! ZipEntry.new(TEST_ZIPFILE, "hello/").file?)
  44. assert(ZipEntry.new(TEST_ZIPFILE, "dir/hello/").directory?)
  45. assert(! ZipEntry.new(TEST_ZIPFILE, "dir/hello/").file?)
  46. end
  47. def test_equality
  48. entry1 = ZipEntry.new("file.zip", "name", "isNotCompared",
  49. "something extra", 123, 1234,
  50. ZipEntry::DEFLATED, 10000)
  51. entry2 = ZipEntry.new("file.zip", "name", "isNotComparedXXX",
  52. "something extra", 123, 1234,
  53. ZipEntry::DEFLATED, 10000)
  54. entry3 = ZipEntry.new("file.zip", "name2", "isNotComparedXXX",
  55. "something extra", 123, 1234,
  56. ZipEntry::DEFLATED, 10000)
  57. entry4 = ZipEntry.new("file.zip", "name2", "isNotComparedXXX",
  58. "something extraXX", 123, 1234,
  59. ZipEntry::DEFLATED, 10000)
  60. entry5 = ZipEntry.new("file.zip", "name2", "isNotComparedXXX",
  61. "something extraXX", 12, 1234,
  62. ZipEntry::DEFLATED, 10000)
  63. entry6 = ZipEntry.new("file.zip", "name2", "isNotComparedXXX",
  64. "something extraXX", 12, 123,
  65. ZipEntry::DEFLATED, 10000)
  66. entry7 = ZipEntry.new("file.zip", "name2", "isNotComparedXXX",
  67. "something extraXX", 12, 123,
  68. ZipEntry::STORED, 10000)
  69. entry8 = ZipEntry.new("file.zip", "name2", "isNotComparedXXX",
  70. "something extraXX", 12, 123,
  71. ZipEntry::STORED, 100000)
  72. assert_equal(entry1, entry1)
  73. assert_equal(entry1, entry2)
  74. assert(entry2 != entry3)
  75. assert(entry3 != entry4)
  76. assert(entry4 != entry5)
  77. assert(entry5 != entry6)
  78. assert(entry6 != entry7)
  79. assert(entry7 != entry8)
  80. assert(entry7 != "hello")
  81. assert(entry7 != 12)
  82. end
  83. def test_compare
  84. assert_equal(0, (ZipEntry.new("zf.zip", "a") <=> ZipEntry.new("zf.zip", "a")))
  85. assert_equal(1, (ZipEntry.new("zf.zip", "b") <=> ZipEntry.new("zf.zip", "a")))
  86. assert_equal(-1, (ZipEntry.new("zf.zip", "a") <=> ZipEntry.new("zf.zip", "b")))
  87. entries = [
  88. ZipEntry.new("zf.zip", "5"),
  89. ZipEntry.new("zf.zip", "1"),
  90. ZipEntry.new("zf.zip", "3"),
  91. ZipEntry.new("zf.zip", "4"),
  92. ZipEntry.new("zf.zip", "0"),
  93. ZipEntry.new("zf.zip", "2")
  94. ]
  95. entries.sort!
  96. assert_equal("0", entries[0].to_s)
  97. assert_equal("1", entries[1].to_s)
  98. assert_equal("2", entries[2].to_s)
  99. assert_equal("3", entries[3].to_s)
  100. assert_equal("4", entries[4].to_s)
  101. assert_equal("5", entries[5].to_s)
  102. end
  103. def test_parentAsString
  104. entry1 = ZipEntry.new("zf.zip", "aa")
  105. entry2 = ZipEntry.new("zf.zip", "aa/")
  106. entry3 = ZipEntry.new("zf.zip", "aa/bb")
  107. entry4 = ZipEntry.new("zf.zip", "aa/bb/")
  108. entry5 = ZipEntry.new("zf.zip", "aa/bb/cc")
  109. entry6 = ZipEntry.new("zf.zip", "aa/bb/cc/")
  110. assert_equal(nil, entry1.parent_as_string)
  111. assert_equal(nil, entry2.parent_as_string)
  112. assert_equal("aa/", entry3.parent_as_string)
  113. assert_equal("aa/", entry4.parent_as_string)
  114. assert_equal("aa/bb/", entry5.parent_as_string)
  115. assert_equal("aa/bb/", entry6.parent_as_string)
  116. end
  117. def test_entry_name_cannot_start_with_slash
  118. assert_raise(ZipEntryNameError) { ZipEntry.new("zf.zip", "/hej/der") }
  119. end
  120. end
  121. module IOizeString
  122. attr_reader :tell
  123. def read(count = nil)
  124. @tell ||= 0
  125. count = size unless count
  126. retVal = slice(@tell, count)
  127. @tell += count
  128. return retVal
  129. end
  130. def seek(index, offset)
  131. @tell ||= 0
  132. case offset
  133. when IO::SEEK_END
  134. newPos = size + index
  135. when IO::SEEK_SET
  136. newPos = index
  137. when IO::SEEK_CUR
  138. newPos = @tell + index
  139. else
  140. raise "Error in test method IOizeString::seek"
  141. end
  142. if (newPos < 0 || newPos >= size)
  143. raise Errno::EINVAL
  144. else
  145. @tell=newPos
  146. end
  147. end
  148. def reset
  149. @tell = 0
  150. end
  151. end
  152. class ZipLocalEntryTest < Test::Unit::TestCase
  153. def test_read_local_entryHeaderOfFirstTestZipEntry
  154. File.open(TestZipFile::TEST_ZIP3.zip_name, "rb") {
  155. |file|
  156. entry = ZipEntry.read_local_entry(file)
  157. assert_equal("", entry.comment)
  158. # Differs from windows and unix because of CR LF
  159. # assert_equal(480, entry.compressed_size)
  160. # assert_equal(0x2a27930f, entry.crc)
  161. # extra field is 21 bytes long
  162. # probably contains some unix attrutes or something
  163. # disabled: assert_equal(nil, entry.extra)
  164. assert_equal(ZipEntry::DEFLATED, entry.compression_method)
  165. assert_equal(TestZipFile::TEST_ZIP3.entry_names[0], entry.name)
  166. assert_equal(File.size(TestZipFile::TEST_ZIP3.entry_names[0]), entry.size)
  167. assert(! entry.is_directory)
  168. }
  169. end
  170. def test_readDateTime
  171. File.open("data/rubycode.zip", "rb") {
  172. |file|
  173. entry = ZipEntry.read_local_entry(file)
  174. assert_equal("zippedruby1.rb", entry.name)
  175. assert_equal(Time.at(1019261638), entry.time)
  176. }
  177. end
  178. def test_read_local_entryFromNonZipFile
  179. File.open("data/file2.txt") {
  180. |file|
  181. assert_equal(nil, ZipEntry.read_local_entry(file))
  182. }
  183. end
  184. def test_read_local_entryFromTruncatedZipFile
  185. zipFragment=""
  186. File.open(TestZipFile::TEST_ZIP2.zip_name) { |f| zipFragment = f.read(12) } # local header is at least 30 bytes
  187. zipFragment.extend(IOizeString).reset
  188. entry = ZipEntry.new
  189. entry.read_local_entry(zipFragment)
  190. fail "ZipError expected"
  191. rescue ZipError
  192. end
  193. def test_writeEntry
  194. entry = ZipEntry.new("file.zip", "entryName", "my little comment",
  195. "thisIsSomeExtraInformation", 100, 987654,
  196. ZipEntry::DEFLATED, 400)
  197. write_to_file("localEntryHeader.bin", "centralEntryHeader.bin", entry)
  198. entryReadLocal, entryReadCentral = read_from_file("localEntryHeader.bin", "centralEntryHeader.bin")
  199. compare_local_entry_headers(entry, entryReadLocal)
  200. compare_c_dir_entry_headers(entry, entryReadCentral)
  201. end
  202. private
  203. def compare_local_entry_headers(entry1, entry2)
  204. assert_equal(entry1.compressed_size , entry2.compressed_size)
  205. assert_equal(entry1.crc , entry2.crc)
  206. assert_equal(entry1.extra , entry2.extra)
  207. assert_equal(entry1.compression_method, entry2.compression_method)
  208. assert_equal(entry1.name , entry2.name)
  209. assert_equal(entry1.size , entry2.size)
  210. assert_equal(entry1.localHeaderOffset, entry2.localHeaderOffset)
  211. end
  212. def compare_c_dir_entry_headers(entry1, entry2)
  213. compare_local_entry_headers(entry1, entry2)
  214. assert_equal(entry1.comment, entry2.comment)
  215. end
  216. def write_to_file(localFileName, centralFileName, entry)
  217. File.open(localFileName, "wb") { |f| entry.write_local_entry(f) }
  218. File.open(centralFileName, "wb") { |f| entry.write_c_dir_entry(f) }
  219. end
  220. def read_from_file(localFileName, centralFileName)
  221. localEntry = nil
  222. cdirEntry = nil
  223. File.open(localFileName, "rb") { |f| localEntry = ZipEntry.read_local_entry(f) }
  224. File.open(centralFileName, "rb") { |f| cdirEntry = ZipEntry.read_c_dir_entry(f) }
  225. return [localEntry, cdirEntry]
  226. end
  227. end
  228. module DecompressorTests
  229. # expects @refText, @refLines and @decompressor
  230. TEST_FILE="data/file1.txt"
  231. def setup
  232. @refText=""
  233. File.open(TEST_FILE) { |f| @refText = f.read }
  234. @refLines = @refText.split($/)
  235. end
  236. def test_readEverything
  237. assert_equal(@refText, @decompressor.sysread)
  238. end
  239. def test_readInChunks
  240. chunkSize = 5
  241. while (decompressedChunk = @decompressor.sysread(chunkSize))
  242. assert_equal(@refText.slice!(0, chunkSize), decompressedChunk)
  243. end
  244. assert_equal(0, @refText.size)
  245. end
  246. def test_mixingReadsAndProduceInput
  247. # Just some preconditions to make sure we have enough data for this test
  248. assert(@refText.length > 1000)
  249. assert(@refLines.length > 40)
  250. assert_equal(@refText[0...100], @decompressor.sysread(100))
  251. assert(! @decompressor.input_finished?)
  252. buf = @decompressor.produce_input
  253. assert_equal(@refText[100...(100+buf.length)], buf)
  254. end
  255. end
  256. class InflaterTest < Test::Unit::TestCase
  257. include DecompressorTests
  258. def setup
  259. super
  260. @file = File.new("data/file1.txt.deflatedData", "rb")
  261. @decompressor = Inflater.new(@file)
  262. end
  263. def teardown
  264. @file.close
  265. end
  266. end
  267. class PassThruDecompressorTest < Test::Unit::TestCase
  268. include DecompressorTests
  269. def setup
  270. super
  271. @file = File.new(TEST_FILE)
  272. @decompressor = PassThruDecompressor.new(@file, File.size(TEST_FILE))
  273. end
  274. def teardown
  275. @file.close
  276. end
  277. end
  278. module AssertEntry
  279. def assert_next_entry(filename, zis)
  280. assert_entry(filename, zis, zis.get_next_entry.name)
  281. end
  282. def assert_entry(filename, zis, entryName)
  283. assert_equal(filename, entryName)
  284. assert_entryContentsForStream(filename, zis, entryName)
  285. end
  286. def assert_entryContentsForStream(filename, zis, entryName)
  287. File.open(filename, "rb") {
  288. |file|
  289. expected = file.read
  290. actual = zis.read
  291. if (expected != actual)
  292. if ((expected && actual) && (expected.length > 400 || actual.length > 400))
  293. zipEntryFilename=entryName+".zipEntry"
  294. File.open(zipEntryFilename, "wb") { |file| file << actual }
  295. fail("File '#{filename}' is different from '#{zipEntryFilename}'")
  296. else
  297. assert_equal(expected, actual)
  298. end
  299. end
  300. }
  301. end
  302. def AssertEntry.assert_contents(filename, aString)
  303. fileContents = ""
  304. File.open(filename, "rb") { |f| fileContents = f.read }
  305. if (fileContents != aString)
  306. if (fileContents.length > 400 || aString.length > 400)
  307. stringFile = filename + ".other"
  308. File.open(stringFile, "wb") { |f| f << aString }
  309. fail("File '#{filename}' is different from contents of string stored in '#{stringFile}'")
  310. else
  311. assert_equal(fileContents, aString)
  312. end
  313. end
  314. end
  315. def assert_stream_contents(zis, testZipFile)
  316. assert(zis != nil)
  317. testZipFile.entry_names.each {
  318. |entryName|
  319. assert_next_entry(entryName, zis)
  320. }
  321. assert_equal(nil, zis.get_next_entry)
  322. end
  323. def assert_test_zip_contents(testZipFile)
  324. ZipInputStream.open(testZipFile.zip_name) {
  325. |zis|
  326. assert_stream_contents(zis, testZipFile)
  327. }
  328. end
  329. def assert_entryContents(zipFile, entryName, filename = entryName.to_s)
  330. zis = zipFile.get_input_stream(entryName)
  331. assert_entryContentsForStream(filename, zis, entryName)
  332. ensure
  333. zis.close if zis
  334. end
  335. end
  336. class ZipInputStreamTest < Test::Unit::TestCase
  337. include AssertEntry
  338. def test_new
  339. zis = ZipInputStream.new(TestZipFile::TEST_ZIP2.zip_name)
  340. assert_stream_contents(zis, TestZipFile::TEST_ZIP2)
  341. assert_equal(true, zis.eof?)
  342. zis.close
  343. end
  344. def test_openWithBlock
  345. ZipInputStream.open(TestZipFile::TEST_ZIP2.zip_name) {
  346. |zis|
  347. assert_stream_contents(zis, TestZipFile::TEST_ZIP2)
  348. assert_equal(true, zis.eof?)
  349. }
  350. end
  351. def test_openWithoutBlock
  352. zis = ZipInputStream.open(TestZipFile::TEST_ZIP2.zip_name)
  353. assert_stream_contents(zis, TestZipFile::TEST_ZIP2)
  354. end
  355. def test_incompleteReads
  356. ZipInputStream.open(TestZipFile::TEST_ZIP2.zip_name) {
  357. |zis|
  358. entry = zis.get_next_entry # longAscii.txt
  359. assert_equal(false, zis.eof?)
  360. assert_equal(TestZipFile::TEST_ZIP2.entry_names[0], entry.name)
  361. assert zis.gets.length > 0
  362. assert_equal(false, zis.eof?)
  363. entry = zis.get_next_entry # empty.txt
  364. assert_equal(TestZipFile::TEST_ZIP2.entry_names[1], entry.name)
  365. assert_equal(0, entry.size)
  366. assert_equal(nil, zis.gets)
  367. assert_equal(true, zis.eof?)
  368. entry = zis.get_next_entry # empty_chmod640.txt
  369. assert_equal(TestZipFile::TEST_ZIP2.entry_names[2], entry.name)
  370. assert_equal(0, entry.size)
  371. assert_equal(nil, zis.gets)
  372. assert_equal(true, zis.eof?)
  373. entry = zis.get_next_entry # short.txt
  374. assert_equal(TestZipFile::TEST_ZIP2.entry_names[3], entry.name)
  375. assert zis.gets.length > 0
  376. entry = zis.get_next_entry # longBinary.bin
  377. assert_equal(TestZipFile::TEST_ZIP2.entry_names[4], entry.name)
  378. assert zis.gets.length > 0
  379. }
  380. end
  381. def test_rewind
  382. ZipInputStream.open(TestZipFile::TEST_ZIP2.zip_name) {
  383. |zis|
  384. e = zis.get_next_entry
  385. assert_equal(TestZipFile::TEST_ZIP2.entry_names[0], e.name)
  386. # Do a little reading
  387. buf = ""
  388. buf << zis.read(100)
  389. buf << (zis.gets || "")
  390. buf << (zis.gets || "")
  391. assert_equal(false, zis.eof?)
  392. zis.rewind
  393. buf2 = ""
  394. buf2 << zis.read(100)
  395. buf2 << (zis.gets || "")
  396. buf2 << (zis.gets || "")
  397. assert_equal(buf, buf2)
  398. zis.rewind
  399. assert_equal(false, zis.eof?)
  400. assert_entry(e.name, zis, e.name)
  401. }
  402. end
  403. def test_mix_read_and_gets
  404. ZipInputStream.open(TestZipFile::TEST_ZIP2.zip_name) {
  405. |zis|
  406. e = zis.get_next_entry
  407. assert_equal("#!/usr/bin/env ruby", zis.gets.chomp)
  408. assert_equal(false, zis.eof?)
  409. assert_equal("", zis.gets.chomp)
  410. assert_equal(false, zis.eof?)
  411. assert_equal("$VERBOSE =", zis.read(10))
  412. assert_equal(false, zis.eof?)
  413. }
  414. end
  415. end
  416. module CrcTest
  417. class TestOutputStream
  418. include IOExtras::AbstractOutputStream
  419. attr_accessor :buffer
  420. def initialize
  421. @buffer = ""
  422. end
  423. def << (data)
  424. @buffer << data
  425. self
  426. end
  427. end
  428. def run_crc_test(compressorClass)
  429. str = "Here's a nice little text to compute the crc for! Ho hum, it is nice nice nice nice indeed."
  430. fakeOut = TestOutputStream.new
  431. deflater = compressorClass.new(fakeOut)
  432. deflater << str
  433. assert_equal(0x919920fc, deflater.crc)
  434. end
  435. end
  436. class PassThruCompressorTest < Test::Unit::TestCase
  437. include CrcTest
  438. def test_size
  439. File.open("dummy.txt", "wb") {
  440. |file|
  441. compressor = PassThruCompressor.new(file)
  442. assert_equal(0, compressor.size)
  443. t1 = "hello world"
  444. t2 = ""
  445. t3 = "bingo"
  446. compressor << t1
  447. assert_equal(compressor.size, t1.size)
  448. compressor << t2
  449. assert_equal(compressor.size, t1.size + t2.size)
  450. compressor << t3
  451. assert_equal(compressor.size, t1.size + t2.size + t3.size)
  452. }
  453. end
  454. def test_crc
  455. run_crc_test(PassThruCompressor)
  456. end
  457. end
  458. class DeflaterTest < Test::Unit::TestCase
  459. include CrcTest
  460. def test_outputOperator
  461. txt = load_file("data/file2.txt")
  462. deflate(txt, "deflatertest.bin")
  463. inflatedTxt = inflate("deflatertest.bin")
  464. assert_equal(txt, inflatedTxt)
  465. end
  466. private
  467. def load_file(fileName)
  468. txt = nil
  469. File.open(fileName, "rb") { |f| txt = f.read }
  470. end
  471. def deflate(data, fileName)
  472. File.open(fileName, "wb") {
  473. |file|
  474. deflater = Deflater.new(file)
  475. deflater << data
  476. deflater.finish
  477. assert_equal(deflater.size, data.size)
  478. file << "trailing data for zlib with -MAX_WBITS"
  479. }
  480. end
  481. def inflate(fileName)
  482. txt = nil
  483. File.open(fileName, "rb") {
  484. |file|
  485. inflater = Inflater.new(file)
  486. txt = inflater.sysread
  487. }
  488. end
  489. def test_crc
  490. run_crc_test(Deflater)
  491. end
  492. end
  493. class ZipOutputStreamTest < Test::Unit::TestCase
  494. include AssertEntry
  495. TEST_ZIP = TestZipFile::TEST_ZIP2.clone
  496. TEST_ZIP.zip_name = "output.zip"
  497. def test_new
  498. zos = ZipOutputStream.new(TEST_ZIP.zip_name)
  499. zos.comment = TEST_ZIP.comment
  500. write_test_zip(zos)
  501. zos.close
  502. assert_test_zip_contents(TEST_ZIP)
  503. end
  504. def test_open
  505. ZipOutputStream.open(TEST_ZIP.zip_name) {
  506. |zos|
  507. zos.comment = TEST_ZIP.comment
  508. write_test_zip(zos)
  509. }
  510. assert_test_zip_contents(TEST_ZIP)
  511. end
  512. def test_writingToClosedStream
  513. assert_i_o_error_in_closed_stream { |zos| zos << "hello world" }
  514. assert_i_o_error_in_closed_stream { |zos| zos.puts "hello world" }
  515. assert_i_o_error_in_closed_stream { |zos| zos.write "hello world" }
  516. end
  517. def test_cannotOpenFile
  518. name = TestFiles::EMPTY_TEST_DIR
  519. begin
  520. zos = ZipOutputStream.open(name)
  521. rescue Exception
  522. assert($!.kind_of?(Errno::EISDIR) || # Linux
  523. $!.kind_of?(Errno::EEXIST) || # Windows/cygwin
  524. $!.kind_of?(Errno::EACCES), # Windows
  525. "Expected Errno::EISDIR (or on win/cygwin: Errno::EEXIST), but was: #{$!.class}")
  526. end
  527. end
  528. def test_put_next_entry
  529. stored_text = "hello world in stored text"
  530. entry_name = "file1"
  531. comment = "my comment"
  532. ZipOutputStream.open(TEST_ZIP.zip_name) do
  533. |zos|
  534. zos.put_next_entry(entry_name, comment, nil, ZipEntry::STORED)
  535. zos << stored_text
  536. end
  537. assert(File.read(TEST_ZIP.zip_name).grep(stored_text))
  538. ZipFile.open(TEST_ZIP.zip_name) do
  539. |zf|
  540. assert_equal(stored_text, zf.read(entry_name))
  541. end
  542. end
  543. def assert_i_o_error_in_closed_stream
  544. assert_raise(IOError) {
  545. zos = ZipOutputStream.new("test_putOnClosedStream.zip")
  546. zos.close
  547. yield zos
  548. }
  549. end
  550. def write_test_zip(zos)
  551. TEST_ZIP.entry_names.each {
  552. |entryName|
  553. zos.put_next_entry(entryName)
  554. File.open(entryName, "rb") { |f| zos.write(f.read) }
  555. }
  556. end
  557. end
  558. module Enumerable
  559. def compare_enumerables(otherEnumerable)
  560. otherAsArray = otherEnumerable.to_a
  561. index=0
  562. each_with_index {
  563. |element, index|
  564. return false unless yield(element, otherAsArray[index])
  565. }
  566. return index+1 == otherAsArray.size
  567. end
  568. end
  569. class ZipCentralDirectoryEntryTest < Test::Unit::TestCase
  570. def test_read_from_stream
  571. File.open("data/testDirectory.bin", "rb") {
  572. |file|
  573. entry = ZipEntry.read_c_dir_entry(file)
  574. assert_equal("longAscii.txt", entry.name)
  575. assert_equal(ZipEntry::DEFLATED, entry.compression_method)
  576. assert_equal(106490, entry.size)
  577. assert_equal(3784, entry.compressed_size)
  578. assert_equal(0xfcd1799c, entry.crc)
  579. assert_equal("", entry.comment)
  580. entry = ZipEntry.read_c_dir_entry(file)
  581. assert_equal("empty.txt", entry.name)
  582. assert_equal(ZipEntry::STORED, entry.compression_method)
  583. assert_equal(0, entry.size)
  584. assert_equal(0, entry.compressed_size)
  585. assert_equal(0x0, entry.crc)
  586. assert_equal("", entry.comment)
  587. entry = ZipEntry.read_c_dir_entry(file)
  588. assert_equal("short.txt", entry.name)
  589. assert_equal(ZipEntry::STORED, entry.compression_method)
  590. assert_equal(6, entry.size)
  591. assert_equal(6, entry.compressed_size)
  592. assert_equal(0xbb76fe69, entry.crc)
  593. assert_equal("", entry.comment)
  594. entry = ZipEntry.read_c_dir_entry(file)
  595. assert_equal("longBinary.bin", entry.name)
  596. assert_equal(ZipEntry::DEFLATED, entry.compression_method)
  597. assert_equal(1000024, entry.size)
  598. assert_equal(70847, entry.compressed_size)
  599. assert_equal(0x10da7d59, entry.crc)
  600. assert_equal("", entry.comment)
  601. entry = ZipEntry.read_c_dir_entry(file)
  602. assert_equal(nil, entry)
  603. # Fields that are not check by this test:
  604. # version made by 2 bytes
  605. # version needed to extract 2 bytes
  606. # general purpose bit flag 2 bytes
  607. # last mod file time 2 bytes
  608. # last mod file date 2 bytes
  609. # compressed size 4 bytes
  610. # uncompressed size 4 bytes
  611. # disk number start 2 bytes
  612. # internal file attributes 2 bytes
  613. # external file attributes 4 bytes
  614. # relative offset of local header 4 bytes
  615. # file name (variable size)
  616. # extra field (variable size)
  617. # file comment (variable size)
  618. }
  619. end
  620. def test_ReadEntryFromTruncatedZipFile
  621. fragment=""
  622. File.open("data/testDirectory.bin") { |f| fragment = f.read(12) } # cdir entry header is at least 46 bytes
  623. fragment.extend(IOizeString)
  624. entry = ZipEntry.new
  625. entry.read_c_dir_entry(fragment)
  626. fail "ZipError expected"
  627. rescue ZipError
  628. end
  629. end
  630. class ZipEntrySetTest < Test::Unit::TestCase
  631. ZIP_ENTRIES = [
  632. ZipEntry.new("zipfile.zip", "name1", "comment1"),
  633. ZipEntry.new("zipfile.zip", "name2", "comment1"),
  634. ZipEntry.new("zipfile.zip", "name3", "comment1"),
  635. ZipEntry.new("zipfile.zip", "name4", "comment1"),
  636. ZipEntry.new("zipfile.zip", "name5", "comment1"),
  637. ZipEntry.new("zipfile.zip", "name6", "comment1")
  638. ]
  639. def setup
  640. @zipEntrySet = ZipEntrySet.new(ZIP_ENTRIES)
  641. end
  642. def test_include
  643. assert(@zipEntrySet.include?(ZIP_ENTRIES.first))
  644. assert(! @zipEntrySet.include?(ZipEntry.new("different.zip", "different", "aComment")))
  645. end
  646. def test_size
  647. assert_equal(ZIP_ENTRIES.size, @zipEntrySet.size)
  648. assert_equal(ZIP_ENTRIES.size, @zipEntrySet.length)
  649. @zipEntrySet << ZipEntry.new("a", "b", "c")
  650. assert_equal(ZIP_ENTRIES.size + 1, @zipEntrySet.length)
  651. end
  652. def test_add
  653. zes = ZipEntrySet.new
  654. entry1 = ZipEntry.new("zf.zip", "name1")
  655. entry2 = ZipEntry.new("zf.zip", "name2")
  656. zes << entry1
  657. assert(zes.include?(entry1))
  658. zes.push(entry2)
  659. assert(zes.include?(entry2))
  660. end
  661. def test_delete
  662. assert_equal(ZIP_ENTRIES.size, @zipEntrySet.size)
  663. entry = @zipEntrySet.delete(ZIP_ENTRIES.first)
  664. assert_equal(ZIP_ENTRIES.size - 1, @zipEntrySet.size)
  665. assert_equal(ZIP_ENTRIES.first, entry)
  666. entry = @zipEntrySet.delete(ZIP_ENTRIES.first)
  667. assert_equal(ZIP_ENTRIES.size - 1, @zipEntrySet.size)
  668. assert_nil(entry)
  669. end
  670. def test_each
  671. # Tested indirectly via each_with_index
  672. count = 0
  673. @zipEntrySet.each_with_index {
  674. |entry, index|
  675. assert(ZIP_ENTRIES.include?(entry))
  676. count = count.succ
  677. }
  678. assert_equal(ZIP_ENTRIES.size, count)
  679. end
  680. def test_entries
  681. assert_equal(ZIP_ENTRIES.sort, @zipEntrySet.entries.sort)
  682. end
  683. def test_compound
  684. newEntry = ZipEntry.new("zf.zip", "new entry", "new entry's comment")
  685. assert_equal(ZIP_ENTRIES.size, @zipEntrySet.size)
  686. @zipEntrySet << newEntry
  687. assert_equal(ZIP_ENTRIES.size + 1, @zipEntrySet.size)
  688. assert(@zipEntrySet.include?(newEntry))
  689. @zipEntrySet.delete(newEntry)
  690. assert_equal(ZIP_ENTRIES.size, @zipEntrySet.size)
  691. end
  692. def test_dup
  693. copy = @zipEntrySet.dup
  694. assert_equal(@zipEntrySet, copy)
  695. # demonstrate that this is a deep copy
  696. copy.entries[0].name = "a totally different name"
  697. assert(@zipEntrySet != copy)
  698. end
  699. def test_parent
  700. entries = [
  701. ZipEntry.new("zf.zip", "a"),
  702. ZipEntry.new("zf.zip", "a/"),
  703. ZipEntry.new("zf.zip", "a/b"),
  704. ZipEntry.new("zf.zip", "a/b/"),
  705. ZipEntry.new("zf.zip", "a/b/c"),
  706. ZipEntry.new("zf.zip", "a/b/c/")
  707. ]
  708. entrySet = ZipEntrySet.new(entries)
  709. assert_equal(nil, entrySet.parent(entries[0]))
  710. assert_equal(nil, entrySet.parent(entries[1]))
  711. assert_equal(entries[1], entrySet.parent(entries[2]))
  712. assert_equal(entries[1], entrySet.parent(entries[3]))
  713. assert_equal(entries[3], entrySet.parent(entries[4]))
  714. assert_equal(entries[3], entrySet.parent(entries[5]))
  715. end
  716. def test_glob
  717. res = @zipEntrySet.glob('name[2-4]')
  718. assert_equal(3, res.size)
  719. assert_equal(ZIP_ENTRIES[1,3], res)
  720. end
  721. def test_glob2
  722. entries = [
  723. ZipEntry.new("zf.zip", "a/"),
  724. ZipEntry.new("zf.zip", "a/b/b1"),
  725. ZipEntry.new("zf.zip", "a/b/c/"),
  726. ZipEntry.new("zf.zip", "a/b/c/c1")
  727. ]
  728. entrySet = ZipEntrySet.new(entries)
  729. assert_equal(entries[0,1], entrySet.glob("*"))
  730. # assert_equal(entries[FIXME], entrySet.glob("**"))
  731. # res = entrySet.glob('a*')
  732. # assert_equal(entries.size, res.size)
  733. # assert_equal(entrySet.map { |e| e.name }, res.map { |e| e.name })
  734. end
  735. end
  736. class ZipCentralDirectoryTest < Test::Unit::TestCase
  737. def test_read_from_stream
  738. File.open(TestZipFile::TEST_ZIP2.zip_name, "rb") {
  739. |zipFile|
  740. cdir = ZipCentralDirectory.read_from_stream(zipFile)
  741. assert_equal(TestZipFile::TEST_ZIP2.entry_names.size, cdir.size)
  742. assert(cdir.entries.sort.compare_enumerables(TestZipFile::TEST_ZIP2.entry_names.sort) {
  743. |cdirEntry, testEntryName|
  744. cdirEntry.name == testEntryName
  745. })
  746. assert_equal(TestZipFile::TEST_ZIP2.comment, cdir.comment)
  747. }
  748. end
  749. def test_readFromInvalidStream
  750. File.open("data/file2.txt", "rb") {
  751. |zipFile|
  752. cdir = ZipCentralDirectory.new
  753. cdir.read_from_stream(zipFile)
  754. }
  755. fail "ZipError expected!"
  756. rescue ZipError
  757. end
  758. def test_ReadFromTruncatedZipFile
  759. fragment=""
  760. File.open("data/testDirectory.bin") { |f| fragment = f.read }
  761. fragment.slice!(12) # removed part of first cdir entry. eocd structure still complete
  762. fragment.extend(IOizeString)
  763. entry = ZipCentralDirectory.new
  764. entry.read_from_stream(fragment)
  765. fail "ZipError expected"
  766. rescue ZipError
  767. end
  768. def test_write_to_stream
  769. entries = [ ZipEntry.new("file.zip", "flimse", "myComment", "somethingExtra"),
  770. ZipEntry.new("file.zip", "secondEntryName"),
  771. ZipEntry.new("file.zip", "lastEntry.txt", "Has a comment too") ]
  772. cdir = ZipCentralDirectory.new(entries, "my zip comment")
  773. File.open("cdirtest.bin", "wb") { |f| cdir.write_to_stream(f) }
  774. cdirReadback = ZipCentralDirectory.new
  775. File.open("cdirtest.bin", "rb") { |f| cdirReadback.read_from_stream(f) }
  776. assert_equal(cdir.entries.sort, cdirReadback.entries.sort)
  777. end
  778. def test_equality
  779. cdir1 = ZipCentralDirectory.new([ ZipEntry.new("file.zip", "flimse", nil,
  780. "somethingExtra"),
  781. ZipEntry.new("file.zip", "secondEntryName"),
  782. ZipEntry.new("file.zip", "lastEntry.txt") ],
  783. "my zip comment")
  784. cdir2 = ZipCentralDirectory.new([ ZipEntry.new("file.zip", "flimse", nil,
  785. "somethingExtra"),
  786. ZipEntry.new("file.zip", "secondEntryName"),
  787. ZipEntry.new("file.zip", "lastEntry.txt") ],
  788. "my zip comment")
  789. cdir3 = ZipCentralDirectory.new([ ZipEntry.new("file.zip", "flimse", nil,
  790. "somethingExtra"),
  791. ZipEntry.new("file.zip", "secondEntryName"),
  792. ZipEntry.new("file.zip", "lastEntry.txt") ],
  793. "comment?")
  794. cdir4 = ZipCentralDirectory.new([ ZipEntry.new("file.zip", "flimse", nil,
  795. "somethingExtra"),
  796. ZipEntry.new("file.zip", "lastEntry.txt") ],
  797. "comment?")
  798. assert_equal(cdir1, cdir1)
  799. assert_equal(cdir1, cdir2)
  800. assert(cdir1 != cdir3)
  801. assert(cdir2 != cdir3)
  802. assert(cdir2 != cdir3)
  803. assert(cdir3 != cdir4)
  804. assert(cdir3 != "hello")
  805. end
  806. end
  807. class BasicZipFileTest < Test::Unit::TestCase
  808. include AssertEntry
  809. def setup
  810. @zipFile = ZipFile.new(TestZipFile::TEST_ZIP2.zip_name)
  811. @testEntryNameIndex=0
  812. end
  813. def test_entries
  814. assert_equal(TestZipFile::TEST_ZIP2.entry_names.sort,
  815. @zipFile.entries.entries.sort.map {|e| e.name} )
  816. end
  817. def test_each
  818. count = 0
  819. visited = {}
  820. @zipFile.each {
  821. |entry|
  822. assert(TestZipFile::TEST_ZIP2.entry_names.include?(entry.name))
  823. assert(! visited.include?(entry.name))
  824. visited[entry.name] = nil
  825. count = count.succ
  826. }
  827. assert_equal(TestZipFile::TEST_ZIP2.entry_names.length, count)
  828. end
  829. def test_foreach
  830. count = 0
  831. visited = {}
  832. ZipFile.foreach(TestZipFile::TEST_ZIP2.zip_name) {
  833. |entry|
  834. assert(TestZipFile::TEST_ZIP2.entry_names.include?(entry.name))
  835. assert(! visited.include?(entry.name))
  836. visited[entry.name] = nil
  837. count = count.succ
  838. }
  839. assert_equal(TestZipFile::TEST_ZIP2.entry_names.length, count)
  840. end
  841. def test_get_input_stream
  842. count = 0
  843. visited = {}
  844. @zipFile.each {
  845. |entry|
  846. assert_entry(entry.name, @zipFile.get_input_stream(entry), entry.name)
  847. assert(! visited.include?(entry.name))
  848. visited[entry.name] = nil
  849. count = count.succ
  850. }
  851. assert_equal(TestZipFile::TEST_ZIP2.entry_names.length, count)
  852. end
  853. def test_get_input_streamBlock
  854. fileAndEntryName = @zipFile.entries.first.name
  855. @zipFile.get_input_stream(fileAndEntryName) {
  856. |zis|
  857. assert_entryContentsForStream(fileAndEntryName,
  858. zis,
  859. fileAndEntryName)
  860. }
  861. end
  862. end
  863. module CommonZipFileFixture
  864. include AssertEntry
  865. EMPTY_FILENAME = "emptyZipFile.zip"
  866. TEST_ZIP = TestZipFile::TEST_ZIP2.clone
  867. TEST_ZIP.zip_name = "5entry_copy.zip"
  868. def setup
  869. File.delete(EMPTY_FILENAME) if File.exists?(EMPTY_FILENAME)
  870. FileUtils.cp(TestZipFile::TEST_ZIP2.zip_name, TEST_ZIP.zip_name)
  871. end
  872. end
  873. class ZipFileTest < Test::Unit::TestCase
  874. include CommonZipFileFixture
  875. def test_createFromScratch
  876. comment = "a short comment"
  877. zf = ZipFile.new(EMPTY_FILENAME, ZipFile::CREATE)
  878. zf.get_output_stream("myFile") { |os| os.write "myFile contains just this" }
  879. zf.mkdir("dir1")
  880. zf.comment = comment
  881. zf.close
  882. zfRead = ZipFile.new(EMPTY_FILENAME)
  883. assert_equal(comment, zfRead.comment)
  884. assert_equal(2, zfRead.entries.length)
  885. end
  886. def test_get_output_stream
  887. entryCount = nil
  888. ZipFile.open(TEST_ZIP.zip_name) {
  889. |zf|
  890. entryCount = zf.size
  891. zf.get_output_stream('newEntry.txt') {
  892. |os|
  893. os.write "Putting stuff in newEntry.txt"
  894. }
  895. assert_equal(entryCount+1, zf.size)
  896. assert_equal("Putting stuff in newEntry.txt", zf.read("newEntry.txt"))
  897. zf.get_output_stream(zf.get_entry('data/generated/empty.txt')) {
  898. |os|
  899. os.write "Putting stuff in data/generated/empty.txt"
  900. }
  901. assert_equal(entryCount+1, zf.size)
  902. assert_equal("Putting stuff in data/generated/empty.txt", zf.read("data/generated/empty.txt"))
  903. zf.get_output_stream('entry.bin') {
  904. |os|
  905. os.write(File.open('data/generated/5entry.zip', 'rb').read)
  906. }
  907. }
  908. ZipFile.open(TEST_ZIP.zip_name) {
  909. |zf|
  910. assert_equal(entryCount+2, zf.size)
  911. assert_equal("Putting stuff in newEntry.txt", zf.read("newEntry.txt"))
  912. assert_equal("Putting stuff in data/generated/empty.txt", zf.read("data/generated/empty.txt"))
  913. assert_equal(File.open('data/generated/5entry.zip', 'rb').read, zf.read("entry.bin"))
  914. }
  915. end
  916. def test_add
  917. srcFile = "data/file2.txt"
  918. entryName = "newEntryName.rb"
  919. assert(File.exists?(srcFile))
  920. zf = ZipFile.new(EMPTY_FILENAME, ZipFile::CREATE)
  921. zf.add(entryName, srcFile)
  922. zf.close
  923. zfRead = ZipFile.new(EMPTY_FILENAME)
  924. assert_equal("", zfRead.comment)
  925. assert_equal(1, zfRead.entries.length)
  926. assert_equal(entryName, zfRead.entries.first.name)
  927. AssertEntry.assert_contents(srcFile,
  928. zfRead.get_input_stream(entryName) { |zis| zis.read })
  929. end
  930. def test_addExistingEntryName
  931. assert_raise(ZipEntryExistsError) {
  932. ZipFile.open(TEST_ZIP.zip_name) {
  933. |zf|
  934. zf.add(zf.entries.first.name, "data/file2.txt")
  935. }
  936. }
  937. end
  938. def test_addExistingEntryNameReplace
  939. gotCalled = false
  940. replacedEntry = nil
  941. ZipFile.open(TEST_ZIP.zip_name) {
  942. |zf|
  943. replacedEntry = zf.entries.first.name
  944. zf.add(replacedEntry, "data/file2.txt") { gotCalled = true; true }
  945. }
  946. assert(gotCalled)
  947. ZipFile.open(TEST_ZIP.zip_name) {
  948. |zf|
  949. assert_contains(zf, replacedEntry, "data/file2.txt")
  950. }
  951. end
  952. def test_addDirectory
  953. ZipFile.open(TEST_ZIP.zip_name) {
  954. |zf|
  955. zf.add(TestFiles::EMPTY_TEST_DIR, TestFiles::EMPTY_TEST_DIR)
  956. }
  957. ZipFile.open(TEST_ZIP.zip_name) {
  958. |zf|
  959. dirEntry = zf.entries.detect { |e| e.name == TestFiles::EMPTY_TEST_DIR+"/" }
  960. assert(dirEntry.is_directory)
  961. }
  962. end
  963. def test_remove
  964. entryToRemove, *remainingEntries = TEST_ZIP.entry_names
  965. FileUtils.cp(TestZipFile::TEST_ZIP2.zip_name, TEST_ZIP.zip_name)
  966. zf = ZipFile.new(TEST_ZIP.zip_name)
  967. assert(zf.entries.map { |e| e.name }.include?(entryToRemove))
  968. zf.remove(entryToRemove)
  969. assert(! zf.entries.map { |e| e.name }.include?(entryToRemove))
  970. assert_equal(zf.entries.map {|x| x.name }.sort, remainingEntries.sort)
  971. zf.close
  972. zfRead = ZipFile.new(TEST_ZIP.zip_name)
  973. assert(! zfRead.entries.map { |e| e.name }.include?(entryToRemove))
  974. assert_equal(zfRead.entries.map {|x| x.name }.sort, remainingEntries.sort)
  975. zfRead.close
  976. end
  977. def test_rename
  978. entryToRename, *remainingEntries = TEST_ZIP.entry_names
  979. zf = ZipFile.new(TEST_ZIP.zip_name)
  980. assert(zf.entries.map { |e| e.name }.include?(entryToRename))
  981. contents = zf.read(entryToRename)
  982. newName = "changed entry name"
  983. assert(! zf.entries.map { |e| e.name }.include?(newName))
  984. zf.rename(entryToRename, newName)
  985. assert(zf.entries.map { |e| e.name }.include?(newName))
  986. assert_equal(contents, zf.read(newName))
  987. zf.close
  988. zfRead = ZipFile.new(TEST_ZIP.zip_name)
  989. assert(zfRead.entries.map { |e| e.name }.include?(newName))
  990. assert_equal(contents, zf.read(newName))
  991. zfRead.close
  992. end
  993. def test_renameToExistingEntry
  994. oldEntries = nil
  995. ZipFile.open(TEST_ZIP.zip_name) { |zf| oldEntries = zf.entries }
  996. assert_raise(ZipEntryExistsError) {
  997. ZipFile.open(TEST_ZIP.zip_name) {
  998. |zf|
  999. zf.rename(zf.entries[0], zf.entries[1].name)
  1000. }
  1001. }
  1002. ZipFile.open(TEST_ZIP.zip_name) {
  1003. |zf|
  1004. assert_equal(oldEntries.sort.map{ |e| e.name }, zf.entries.sort.map{ |e| e.name })
  1005. }
  1006. end
  1007. def test_renameToExistingEntryOverwrite
  1008. oldEntries = nil
  1009. ZipFile.open(TEST_ZIP.zip_name) { |zf| oldEntries = zf.entries }
  1010. gotCalled = false
  1011. renamedEntryName = nil
  1012. ZipFile.open(TEST_ZIP.zip_name) {
  1013. |zf|
  1014. renamedEntryName = zf.entries[0].name
  1015. zf.rename(zf.entries[0], zf.entries[1].name) { gotCalled = true; true }
  1016. }
  1017. assert(gotCalled)
  1018. oldEntries.delete_if { |e| e.name == renamedEntryName }
  1019. ZipFile.open(TEST_ZIP.zip_name) {
  1020. |zf|
  1021. assert_equal(oldEntries.sort.map{ |e| e.name },
  1022. zf.entries.sort.map{ |e| e.name })
  1023. }
  1024. end
  1025. def test_renameNonEntry
  1026. nonEntry = "bogusEntry"
  1027. target_entry = "target_entryName"
  1028. zf = ZipFile.new(TEST_ZIP.zip_name)
  1029. assert(! zf.entries.include?(nonEntry))
  1030. assert_raise(Errno::ENOENT) {
  1031. zf.rename(nonEntry, target_entry)
  1032. }
  1033. zf.commit
  1034. assert(! zf.entries.include?(target_entry))
  1035. ensure
  1036. zf.close
  1037. end
  1038. def test_renameEntryToExistingEntry
  1039. entry1, entry2, *remaining = TEST_ZIP.entry_names
  1040. zf = ZipFile.new(TEST_ZIP.zip_name)
  1041. assert_raise(ZipEntryExistsError) {
  1042. zf.rename(entry1, entry2)
  1043. }
  1044. ensure
  1045. zf.close
  1046. end
  1047. def test_replace
  1048. entryToReplace = TEST_ZIP.entry_names[2]
  1049. newEntrySrcFilename = "data/file2.txt"
  1050. zf = ZipFile.new(TEST_ZIP.zip_name)
  1051. zf.replace(entryToReplace, newEntrySrcFilename)
  1052. zf.close
  1053. zfRead = ZipFile.new(TEST_ZIP.zip_name)
  1054. AssertEntry::assert_contents(newEntrySrcFilename,
  1055. zfRead.get_input_stream(entryToReplace) { |is| is.read })
  1056. AssertEntry::assert_contents(TEST_ZIP.entry_names[0],
  1057. zfRead.get_input_stream(TEST_ZIP.entry_names[0]) { |is| is.read })
  1058. AssertEntry::assert_contents(TEST_ZIP.entry_names[1],
  1059. zfRead.get_input_stream(TEST_ZIP.entry_names[1]) { |is| is.read })
  1060. AssertEntry::assert_contents(TEST_ZIP.entry_names[3],
  1061. zfRead.get_input_stream(TEST_ZIP.entry_names[3]) { |is| is.read })
  1062. zfRead.close
  1063. end
  1064. def test_replaceNonEntry
  1065. entryToReplace = "nonExistingEntryname"
  1066. ZipFile.open(TEST_ZIP.zip_name) {
  1067. |zf|
  1068. assert_raise(Errno::ENOENT) {
  1069. zf.replace(entryToReplace, "data/file2.txt")
  1070. }
  1071. }
  1072. end
  1073. def test_commit
  1074. newName = "renamedFirst"
  1075. zf = ZipFile.new(TEST_ZIP.zip_name)
  1076. oldName = zf.entries.first
  1077. zf.rename(oldName, newName)
  1078. zf.commit
  1079. zfRead = ZipFile.new(TEST_ZIP.zip_name)
  1080. assert(zfRead.entries.detect { |e| e.name == newName } != nil)
  1081. assert(zfRead.entries.detect { |e| e.name == oldName } == nil)
  1082. zfRead.close
  1083. zf.close
  1084. end
  1085. # This test tests that after commit, you
  1086. # can delete the file you used to add the entry to the zip file
  1087. # with
  1088. def test_commitUseZipEntry
  1089. FileUtils.cp(TestFiles::RANDOM_ASCII_FILE1, "okToDelete.txt")
  1090. zf = ZipFile.open(TEST_ZIP.zip_name)
  1091. zf.add("okToDelete.txt", "okToDelete.txt")
  1092. assert_contains(zf, "okToDelete.txt")
  1093. zf.commit
  1094. File.rename("okToDelete.txt", "okToDeleteMoved.txt")
  1095. assert_contains(zf, "okToDelete.txt", "okToDeleteMoved.txt")
  1096. end
  1097. # def test_close
  1098. # zf = ZipFile.new(TEST_ZIP.zip_name)
  1099. # zf.close
  1100. # assert_raise(IOError) {
  1101. # zf.extract(TEST_ZIP.entry_names.first, "hullubullu")
  1102. # }
  1103. # end
  1104. def test_compound1
  1105. renamedName = "renamedName"
  1106. originalEntries = []
  1107. begin
  1108. zf = ZipFile.new(TEST_ZIP.zip_name)
  1109. originalEntries = zf.entries.dup
  1110. assert_not_contains(zf, TestFiles::RANDOM_ASCII_FILE1)
  1111. zf.add(TestFiles::RANDOM_ASCII_FILE1,
  1112. TestFiles::RANDOM_ASCII_FILE1)
  1113. assert_contains(zf, TestFiles::RANDOM_ASCII_FILE1)
  1114. zf.rename(zf.entries[0], renamedName)
  1115. assert_contains(zf, renamedName)
  1116. TestFiles::BINARY_TEST_FILES.each {
  1117. |filename|
  1118. zf.add(filename, filename)
  1119. assert_contains(zf, filename)
  1120. }
  1121. assert_contains(zf, originalEntries.last.to_s)
  1122. zf.remove(originalEntries.last.to_s)
  1123. assert_not_contains(zf, originalEntries.last.to_s)
  1124. ensure
  1125. zf.close
  1126. end
  1127. begin
  1128. zfRead = ZipFile.new(TEST_ZIP.zip_name)
  1129. assert_contains(zfRead, TestFiles::RANDOM_ASCII_FILE1)
  1130. assert_contains(zfRead, renamedName)
  1131. TestFiles::BINARY_TEST_FILES.each {
  1132. |filename|
  1133. assert_contains(zfRead, filename)
  1134. }
  1135. assert_not_contains(zfRead, originalEntries.last.to_s)
  1136. ensure
  1137. zfRead.close
  1138. end
  1139. end
  1140. def test_compound2
  1141. begin
  1142. zf = ZipFile.new(TEST_ZIP.zip_name)
  1143. originalEntries = zf.entries.dup
  1144. originalEntries.each {
  1145. |entry|
  1146. zf.remove(entry)
  1147. assert_not_contains(zf, entry)
  1148. }
  1149. assert(zf.entries.empty?)
  1150. TestFiles::ASCII_TEST_FILES.each {
  1151. |filename|
  1152. zf.add(filename, filename)
  1153. assert_contains(zf, filename)
  1154. }
  1155. assert_equal(zf.entries.sort.map { |e| e.name }, TestFiles::ASCII_TEST_FILES)
  1156. zf.rename(TestFiles::ASCII_TEST_FILES[0], "newName")
  1157. assert_not_contains(zf, TestFiles::ASCII_TEST_FILES[0])
  1158. assert_contains(zf, "newName")
  1159. ensure
  1160. zf.close
  1161. end
  1162. begin
  1163. zfRead = ZipFile.new(TEST_ZIP.zip_name)
  1164. asciiTestFiles = TestFiles::ASCII_TEST_FILES.dup
  1165. asciiTestFiles.shift
  1166. asciiTestFiles.each {
  1167. |filename|
  1168. assert_contains(zf, filename)
  1169. }
  1170. assert_contains(zf, "newName")
  1171. ensure
  1172. zfRead.close
  1173. end
  1174. end
  1175. private
  1176. def assert_contains(zf, entryName, filename = entryName)
  1177. assert(zf.entries.detect { |e| e.name == entryName} != nil, "entry #{entryName} not in #{zf.entries.join(', ')} in zip file #{zf}")
  1178. assert_entryContents(zf, entryName, filename) if File.exists?(filename)
  1179. end
  1180. def assert_not_contains(zf, entryName)
  1181. assert(zf.entries.detect { |e| e.name == entryName} == nil, "entry #{entryName} in #{zf.entries.join(', ')} in zip file #{zf}")
  1182. end
  1183. end
  1184. class ZipFileExtractTest < Test::Unit::TestCase
  1185. include CommonZipFileFixture
  1186. EXTRACTED_FILENAME = "extEntry"
  1187. ENTRY_TO_EXTRACT, *REMAINING_ENTRIES = TEST_ZIP.entry_names.reverse
  1188. def setup
  1189. super
  1190. File.delete(EXTRACTED_FILENAME) if File.exists?(EXTRACTED_FILENAME)
  1191. end
  1192. def test_extract
  1193. ZipFile.open(TEST_ZIP.zip_name) {
  1194. |zf|
  1195. zf.extract(ENTRY_TO_EXTRACT, EXTRACTED_FILENAME)
  1196. assert(File.exists?(EXTRACTED_FILENAME))
  1197. AssertEntry::assert_contents(EXTRACTED_FILENAME,
  1198. zf.get_input_stream(ENTRY_TO_EXTRACT) { |is| is.read })
  1199. File::unlink(EXTRACTED_FILENAME)
  1200. entry = zf.get_entry(ENTRY_TO_EXTRACT)
  1201. entry.extract(EXTRACTED_FILENAME)
  1202. assert(File.exists?(EXTRACTED_FILENAME))
  1203. AssertEntry::assert_contents(EXTRACTED_FILENAME,
  1204. entry.get_input_stream() { |is| is.read })
  1205. }
  1206. end
  1207. def test_extractExists
  1208. writtenText = "written text"
  1209. File.open(EXTRACTED_FILENAME, "w") { |f| f.write(writtenText) }
  1210. assert_raise(ZipDestinationFileExistsError) {
  1211. ZipFile.open(TEST_ZIP.zip_name) {
  1212. |zf|
  1213. zf.extract(zf.entries.first, EXTRACTED_FILENAME)
  1214. }
  1215. }
  1216. File.open(EXTRACTED_FILENAME, "r") {
  1217. |f|
  1218. assert_equal(writtenText, f.read)
  1219. }
  1220. end
  1221. def test_extractExistsOverwrite
  1222. writtenText = "written text"
  1223. File.open(EXTRACTED_FILENAME, "w") { |f| f.write(writtenText) }
  1224. gotCalledCorrectly = false
  1225. ZipFile.open(TEST_ZIP.zip_name) {
  1226. |zf|
  1227. zf.extract(zf.entries.first, EXTRACTED_FILENAME) {
  1228. |entry, extractLoc|
  1229. gotCalledCorrectly = zf.entries.first == entry &&
  1230. extractLoc == EXTRACTED_FILENAME
  1231. true
  1232. }
  1233. }
  1234. assert(gotCalledCorrectly)
  1235. File.open(EXTRACTED_FILENAME, "r") {
  1236. |f|
  1237. assert(writtenText != f.read)
  1238. }
  1239. end
  1240. def test_extractNonEntry
  1241. zf = ZipFile.new(TEST_ZIP.zip_name)
  1242. assert_raise(Errno::ENOENT) { zf.extract("nonExistingEntry", "nonExistingEntry") }
  1243. ensure
  1244. zf.close if zf
  1245. end
  1246. def test_extractNonEntry2
  1247. outFile = "outfile"
  1248. assert_raise(Errno::ENOENT) {
  1249. zf = ZipFile.new(TEST_ZIP.zip_name)
  1250. nonEntry = "hotdog-diddelidoo"
  1251. assert(! zf.entries.include?(nonEntry))
  1252. zf.extract(nonEntry, outFile)
  1253. zf.close
  1254. }
  1255. assert(! File.exists?(outFile))
  1256. end
  1257. end
  1258. class ZipFileExtractDirectoryTest < Test::Unit::TestCase
  1259. include CommonZipFileFixture
  1260. TEST_OUT_NAME = "emptyOutDir"
  1261. def open_zip(&aProc)
  1262. assert(aProc != nil)
  1263. ZipFile.open(TestZipFile::TEST_ZIP4.zip_name, &aProc)
  1264. end
  1265. def extract_test_dir(&aProc)
  1266. open_zip {
  1267. |zf|
  1268. zf.extract(TestFiles::EMPTY_TEST_DIR, TEST_OUT_NAME, &aProc)
  1269. }
  1270. end
  1271. def setup
  1272. super
  1273. Dir.rmdir(TEST_OUT_NAME) if File.directory? TEST_OUT_NAME
  1274. File.delete(TEST_OUT_NAME) if File.exists? TEST_OUT_NAME
  1275. end
  1276. def test_extractDirectory
  1277. extract_test_dir
  1278. assert(File.directory?(TEST_OUT_NAME))
  1279. end
  1280. def test_extractDirectoryExistsAsDir
  1281. Dir.mkdir TEST_OUT_NAME
  1282. extract_test_dir
  1283. assert(File.directory?(TEST_OUT_NAME))
  1284. end
  1285. def test_extractDirectoryExistsAsFile
  1286. File.open(TEST_OUT_NAME, "w") { |f| f.puts "something" }
  1287. assert_raise(ZipDestinationFileExistsError) { extract_test_dir }
  1288. end
  1289. def test_extractDirectoryExistsAsFileOverwrite
  1290. File.open(TEST_OUT_NAME, "w") { |f| f.puts "something" }
  1291. gotCalled = false
  1292. extract_test_dir {
  1293. |entry, destPath|
  1294. gotCalled = true
  1295. assert_equal(TEST_OUT_NAME, destPath)
  1296. assert(entry.is_directory)
  1297. true
  1298. }
  1299. assert(gotCalled)
  1300. assert(File.directory?(TEST_OUT_NAME))
  1301. end
  1302. end
  1303. class ZipExtraFieldTest < Test::Unit::TestCase
  1304. def test_new
  1305. extra_pure = ZipExtraField.new("")
  1306. extra_withstr = ZipExtraField.new("foo")
  1307. assert_instance_of(ZipExtraField, extra_pure)
  1308. assert_instance_of(ZipExtraField, extra_withstr)
  1309. end
  1310. def test_unknownfield
  1311. extra = ZipExtraField.new("foo")
  1312. assert_equal(extra["Unknown"], "foo")
  1313. extra.merge("a")
  1314. assert_equal(extra["Unknown"], "fooa")
  1315. extra.merge("barbaz")
  1316. assert_equal(extra.to_s, "fooabarbaz")
  1317. end
  1318. def test_merge
  1319. str = "UT\x5\0\x3\250$\r@Ux\0\0"
  1320. extra1 = ZipExtraField.new("")
  1321. extra2 = ZipExtraField.new(str)
  1322. assert(! extra1.member?("UniversalTime"))
  1323. assert(extra2.member?("UniversalTime"))
  1324. extra1.merge(str)
  1325. assert_equal(extra1["UniversalTime"].mtime, extra2["UniversalTime"].mtime)
  1326. end
  1327. def test_length
  1328. str = "UT\x5\0\x3\250$\r@Ux\0\0Te\0\0testit"
  1329. extra = ZipExtraField.new(str)
  1330. assert_equal(extra.local_length, extra.to_local_bin.length)
  1331. assert_equal(extra.c_dir_length, extra.to_c_dir_bin.length)
  1332. extra.merge("foo")
  1333. assert_equal(extra.local_length, extra.to_local_bin.length)
  1334. assert_equal(extra.c_dir_length, extra.to_c_dir_bin.length)
  1335. end
  1336. def test_to_s
  1337. str = "UT\x5\0\x3\250$\r@Ux\0\0Te\0\0testit"
  1338. extra = ZipExtraField.new(str)
  1339. assert_instance_of(String, extra.to_s)
  1340. s = extra.to_s
  1341. extra.merge("foo")
  1342. assert_equal(s.length + 3, extra.to_s.length)
  1343. end
  1344. def test_equality
  1345. str = "UT\x5\0\x3\250$\r@"
  1346. extra1 = ZipExtraField.new(str)
  1347. extra2 = ZipExtraField.new(str)
  1348. extra3 = ZipExtraField.new(str)
  1349. assert_equal(extra1, extra2)
  1350. extra2["UniversalTime"].mtime = Time.now
  1351. assert(extra1 != extra2)
  1352. extra3.create("IUnix")
  1353. assert(extra1 != extra3)
  1354. extra1.create("IUnix")
  1355. assert_equal(extra1, extra3)
  1356. end
  1357. end
  1358. # Copyright (C) 2002-2005 Thomas Sondergaard
  1359. # rubyzip is free software; you can redistribute it and/or
  1360. # modify it under the terms of the ruby license.