blob: 5a5099604378c2cebc11a395e74ddc51bb45b2f2 [file] [log] [blame]
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +00001import sys
2import os
3import shutil
Brett Cannon455ea532003-06-12 08:01:06 +00004import tempfile
Georg Brandl38c6a222006-05-10 16:26:03 +00005import StringIO
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +00006
7import unittest
8import tarfile
9
10from test import test_support
11
12# Check for our compression modules.
13try:
14 import gzip
Neal Norwitzae323192003-04-14 01:18:32 +000015 gzip.GzipFile
16except (ImportError, AttributeError):
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +000017 gzip = None
18try:
19 import bz2
20except ImportError:
21 bz2 = None
22
23def path(path):
24 return test_support.findfile(path)
25
Brett Cannon455ea532003-06-12 08:01:06 +000026testtar = path("testtar.tar")
27tempdir = os.path.join(tempfile.gettempdir(), "testtar" + os.extsep + "dir")
28tempname = test_support.TESTFN
Georg Brandl38c6a222006-05-10 16:26:03 +000029membercount = 12
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +000030
31def tarname(comp=""):
32 if not comp:
33 return testtar
Brett Cannon43e559a2003-06-12 19:16:58 +000034 return os.path.join(tempdir, "%s%s%s" % (testtar, os.extsep, comp))
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +000035
36def dirname():
37 if not os.path.exists(tempdir):
38 os.mkdir(tempdir)
39 return tempdir
40
41def tmpname():
42 return tempname
43
44
45class BaseTest(unittest.TestCase):
46 comp = ''
47 mode = 'r'
48 sep = ':'
49
50 def setUp(self):
51 mode = self.mode + self.sep + self.comp
52 self.tar = tarfile.open(tarname(self.comp), mode)
53
54 def tearDown(self):
55 self.tar.close()
56
57class ReadTest(BaseTest):
58
59 def test(self):
60 """Test member extraction.
61 """
62 members = 0
63 for tarinfo in self.tar:
64 members += 1
65 if not tarinfo.isreg():
66 continue
67 f = self.tar.extractfile(tarinfo)
68 self.assert_(len(f.read()) == tarinfo.size,
69 "size read does not match expected size")
70 f.close()
71
72 self.assert_(members == membercount,
73 "could not find all members")
74
75 def test_sparse(self):
76 """Test sparse member extraction.
77 """
78 if self.sep != "|":
79 f1 = self.tar.extractfile("S-SPARSE")
Jack Jansen149a8992003-03-07 13:27:53 +000080 f2 = self.tar.extractfile("S-SPARSE-WITH-NULLS")
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +000081 self.assert_(f1.read() == f2.read(),
82 "_FileObject failed on sparse file member")
83
84 def test_readlines(self):
85 """Test readlines() method of _FileObject.
86 """
87 if self.sep != "|":
Jack Jansen149a8992003-03-07 13:27:53 +000088 filename = "0-REGTYPE-TEXT"
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +000089 self.tar.extract(filename, dirname())
Tim Peters02494762006-05-26 14:02:05 +000090 f = open(os.path.join(dirname(), filename), "rU")
91 lines1 = f.readlines()
92 f.close()
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +000093 lines2 = self.tar.extractfile(filename).readlines()
94 self.assert_(lines1 == lines2,
95 "_FileObject.readline() does not work correctly")
96
Martin v. Löwisdf241532005-03-03 08:17:42 +000097 def test_iter(self):
98 # Test iteration over ExFileObject.
99 if self.sep != "|":
100 filename = "0-REGTYPE-TEXT"
101 self.tar.extract(filename, dirname())
Tim Peters02494762006-05-26 14:02:05 +0000102 f = open(os.path.join(dirname(), filename), "rU")
103 lines1 = f.readlines()
104 f.close()
Martin v. Löwisdf241532005-03-03 08:17:42 +0000105 lines2 = [line for line in self.tar.extractfile(filename)]
106 self.assert_(lines1 == lines2,
107 "ExFileObject iteration does not work correctly")
108
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +0000109 def test_seek(self):
110 """Test seek() method of _FileObject, incl. random reading.
111 """
112 if self.sep != "|":
Lars Gustäbelaedb92e2006-12-23 16:51:47 +0000113 filename = "0-REGTYPE-TEXT"
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +0000114 self.tar.extract(filename, dirname())
Tim Peters02494762006-05-26 14:02:05 +0000115 f = open(os.path.join(dirname(), filename), "rb")
116 data = f.read()
117 f.close()
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +0000118
119 tarinfo = self.tar.getmember(filename)
120 fobj = self.tar.extractfile(tarinfo)
121
122 text = fobj.read()
123 fobj.seek(0)
124 self.assert_(0 == fobj.tell(),
125 "seek() to file's start failed")
126 fobj.seek(2048, 0)
127 self.assert_(2048 == fobj.tell(),
128 "seek() to absolute position failed")
129 fobj.seek(-1024, 1)
130 self.assert_(1024 == fobj.tell(),
131 "seek() to negative relative position failed")
132 fobj.seek(1024, 1)
133 self.assert_(2048 == fobj.tell(),
134 "seek() to positive relative position failed")
135 s = fobj.read(10)
136 self.assert_(s == data[2048:2058],
137 "read() after seek failed")
138 fobj.seek(0, 2)
139 self.assert_(tarinfo.size == fobj.tell(),
140 "seek() to file's end failed")
141 self.assert_(fobj.read() == "",
142 "read() at file's end did not return empty string")
143 fobj.seek(-tarinfo.size, 2)
144 self.assert_(0 == fobj.tell(),
145 "relative seek() to file's start failed")
146 fobj.seek(512)
147 s1 = fobj.readlines()
148 fobj.seek(512)
149 s2 = fobj.readlines()
150 self.assert_(s1 == s2,
151 "readlines() after seek failed")
Lars Gustäbelaedb92e2006-12-23 16:51:47 +0000152 fobj.seek(0)
153 self.assert_(len(fobj.readline()) == fobj.tell(),
154 "tell() after readline() failed")
155 fobj.seek(512)
156 self.assert_(len(fobj.readline()) + 512 == fobj.tell(),
157 "tell() after seek() and readline() failed")
158 fobj.seek(0)
159 line = fobj.readline()
160 self.assert_(fobj.read() == data[len(line):],
161 "read() after readline() failed")
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +0000162 fobj.close()
163
Neal Norwitzf3396542005-10-28 05:52:22 +0000164 def test_old_dirtype(self):
165 """Test old style dirtype member (bug #1336623).
166 """
167 # Old tars create directory members using a REGTYPE
168 # header with a "/" appended to the filename field.
169
170 # Create an old tar style directory entry.
171 filename = tmpname()
172 tarinfo = tarfile.TarInfo("directory/")
173 tarinfo.type = tarfile.REGTYPE
174
Tim Petersb1f32512006-05-26 13:39:17 +0000175 fobj = open(filename, "w")
Neal Norwitzf3396542005-10-28 05:52:22 +0000176 fobj.write(tarinfo.tobuf())
177 fobj.close()
178
179 try:
180 # Test if it is still a directory entry when
181 # read back.
182 tar = tarfile.open(filename)
183 tarinfo = tar.getmembers()[0]
184 tar.close()
185
186 self.assert_(tarinfo.type == tarfile.DIRTYPE)
187 self.assert_(tarinfo.name.endswith("/"))
188 finally:
189 try:
190 os.unlink(filename)
191 except:
192 pass
193
Lars Gustäbeld2201442007-04-20 14:49:02 +0000194 def test_dirtype(self):
195 for tarinfo in self.tar:
196 if tarinfo.isdir():
197 self.assert_(tarinfo.name.endswith("/"))
198 self.assert_(not tarinfo.name[:-1].endswith("/"))
199
200
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +0000201class ReadStreamTest(ReadTest):
202 sep = "|"
203
204 def test(self):
205 """Test member extraction, and for StreamError when
206 seeking backwards.
207 """
208 ReadTest.test(self)
209 tarinfo = self.tar.getmembers()[0]
210 f = self.tar.extractfile(tarinfo)
211 self.assertRaises(tarfile.StreamError, f.read)
212
213 def test_stream(self):
214 """Compare the normal tar and the stream tar.
215 """
216 stream = self.tar
217 tar = tarfile.open(tarname(), 'r')
218
219 while 1:
220 t1 = tar.next()
221 t2 = stream.next()
222 if t1 is None:
223 break
224 self.assert_(t2 is not None, "stream.next() failed.")
225
226 if t2.islnk() or t2.issym():
227 self.assertRaises(tarfile.StreamError, stream.extractfile, t2)
228 continue
229 v1 = tar.extractfile(t1)
230 v2 = stream.extractfile(t2)
231 if v1 is None:
232 continue
233 self.assert_(v2 is not None, "stream.extractfile() failed")
234 self.assert_(v1.read() == v2.read(), "stream extraction failed")
235
Tim Peters02494762006-05-26 14:02:05 +0000236 tar.close()
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +0000237 stream.close()
238
Georg Brandl49c8f4c2006-05-15 19:30:35 +0000239class ReadDetectTest(ReadTest):
240
241 def setUp(self):
242 self.tar = tarfile.open(tarname(self.comp), self.mode)
243
244class ReadDetectFileobjTest(ReadTest):
245
246 def setUp(self):
247 name = tarname(self.comp)
Tim Peters12087ba2006-05-15 20:44:10 +0000248 self.tar = tarfile.open(name, mode=self.mode,
249 fileobj=open(name, "rb"))
Georg Brandl49c8f4c2006-05-15 19:30:35 +0000250
Martin v. Löwis78be7df2005-03-05 12:47:42 +0000251class ReadAsteriskTest(ReadTest):
252
253 def setUp(self):
254 mode = self.mode + self.sep + "*"
255 self.tar = tarfile.open(tarname(self.comp), mode)
256
257class ReadStreamAsteriskTest(ReadStreamTest):
258
259 def setUp(self):
260 mode = self.mode + self.sep + "*"
261 self.tar = tarfile.open(tarname(self.comp), mode)
262
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +0000263class WriteTest(BaseTest):
264 mode = 'w'
265
266 def setUp(self):
267 mode = self.mode + self.sep + self.comp
268 self.src = tarfile.open(tarname(self.comp), 'r')
Martin v. Löwisc234a522004-08-22 21:28:33 +0000269 self.dstname = tmpname()
270 self.dst = tarfile.open(self.dstname, mode)
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +0000271
272 def tearDown(self):
273 self.src.close()
274 self.dst.close()
275
276 def test_posix(self):
277 self.dst.posix = 1
278 self._test()
279
280 def test_nonposix(self):
281 self.dst.posix = 0
282 self._test()
283
Martin v. Löwisc234a522004-08-22 21:28:33 +0000284 def test_small(self):
285 self.dst.add(os.path.join(os.path.dirname(__file__),"cfgparser.1"))
286 self.dst.close()
287 self.assertNotEqual(os.stat(self.dstname).st_size, 0)
288
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +0000289 def _test(self):
290 for tarinfo in self.src:
291 if not tarinfo.isreg():
292 continue
293 f = self.src.extractfile(tarinfo)
Georg Brandl38c6a222006-05-10 16:26:03 +0000294 if self.dst.posix and len(tarinfo.name) > tarfile.LENGTH_NAME and "/" not in tarinfo.name:
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +0000295 self.assertRaises(ValueError, self.dst.addfile,
296 tarinfo, f)
297 else:
298 self.dst.addfile(tarinfo, f)
299
Lars Gustäbel12e087a2006-12-23 18:13:57 +0000300 def test_add_self(self):
301 dstname = os.path.abspath(self.dstname)
302
303 self.assertEqual(self.dst.name, dstname, "archive name must be absolute")
304
305 self.dst.add(dstname)
306 self.assertEqual(self.dst.getnames(), [], "added the archive to itself")
307
308 cwd = os.getcwd()
309 os.chdir(dirname())
310 self.dst.add(dstname)
311 os.chdir(cwd)
312 self.assertEqual(self.dst.getnames(), [], "added the archive to itself")
313
Georg Brandlee23f4b2006-10-24 16:54:23 +0000314
315class Write100Test(BaseTest):
316 # The name field in a tar header stores strings of at most 100 chars.
317 # If a string is shorter than 100 chars it has to be padded with '\0',
318 # which implies that a string of exactly 100 chars is stored without
319 # a trailing '\0'.
320
321 def setUp(self):
322 self.name = "01234567890123456789012345678901234567890123456789"
323 self.name += "01234567890123456789012345678901234567890123456789"
324
325 self.tar = tarfile.open(tmpname(), "w")
326 t = tarfile.TarInfo(self.name)
327 self.tar.addfile(t)
328 self.tar.close()
329
330 self.tar = tarfile.open(tmpname())
331
332 def tearDown(self):
333 self.tar.close()
334
335 def test(self):
336 self.assertEqual(self.tar.getnames()[0], self.name,
337 "failed to store 100 char filename")
338
339
Martin v. Löwis5dbdc592005-08-27 10:07:56 +0000340class WriteSize0Test(BaseTest):
341 mode = 'w'
342
343 def setUp(self):
344 self.tmpdir = dirname()
345 self.dstname = tmpname()
346 self.dst = tarfile.open(self.dstname, "w")
347
348 def tearDown(self):
349 self.dst.close()
350
351 def test_file(self):
352 path = os.path.join(self.tmpdir, "file")
Tim Peters02494762006-05-26 14:02:05 +0000353 f = open(path, "w")
354 f.close()
Martin v. Löwis5dbdc592005-08-27 10:07:56 +0000355 tarinfo = self.dst.gettarinfo(path)
356 self.assertEqual(tarinfo.size, 0)
Tim Peters02494762006-05-26 14:02:05 +0000357 f = open(path, "w")
358 f.write("aaa")
359 f.close()
Martin v. Löwis5dbdc592005-08-27 10:07:56 +0000360 tarinfo = self.dst.gettarinfo(path)
361 self.assertEqual(tarinfo.size, 3)
362
363 def test_directory(self):
364 path = os.path.join(self.tmpdir, "directory")
Tim Peters4ccc0b72006-05-15 21:32:25 +0000365 if os.path.exists(path):
366 # This shouldn't be necessary, but is <wink> if a previous
367 # run was killed in mid-stream.
368 shutil.rmtree(path)
Martin v. Löwis5dbdc592005-08-27 10:07:56 +0000369 os.mkdir(path)
370 tarinfo = self.dst.gettarinfo(path)
371 self.assertEqual(tarinfo.size, 0)
372
373 def test_symlink(self):
374 if hasattr(os, "symlink"):
375 path = os.path.join(self.tmpdir, "symlink")
376 os.symlink("link_target", path)
377 tarinfo = self.dst.gettarinfo(path)
378 self.assertEqual(tarinfo.size, 0)
379
380
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +0000381class WriteStreamTest(WriteTest):
382 sep = '|'
383
Neal Norwitz7443b802006-08-21 18:43:51 +0000384 def test_padding(self):
385 self.dst.close()
386
387 if self.comp == "gz":
388 f = gzip.GzipFile(self.dstname)
389 s = f.read()
390 f.close()
391 elif self.comp == "bz2":
392 f = bz2.BZ2Decompressor()
393 s = file(self.dstname).read()
394 s = f.decompress(s)
395 self.assertEqual(len(f.unused_data), 0, "trailing data")
396 else:
397 f = file(self.dstname)
398 s = f.read()
399 f.close()
400
401 self.assertEqual(s.count("\0"), tarfile.RECORDSIZE,
402 "incorrect zero padding")
403
404
Neal Norwitz0662f8a2004-07-20 21:54:18 +0000405class WriteGNULongTest(unittest.TestCase):
406 """This testcase checks for correct creation of GNU Longname
407 and Longlink extensions.
408
409 It creates a tarfile and adds empty members with either
410 long names, long linknames or both and compares the size
411 of the tarfile with the expected size.
412
413 It checks for SF bug #812325 in TarFile._create_gnulong().
414
415 While I was writing this testcase, I noticed a second bug
416 in the same method:
417 Long{names,links} weren't null-terminated which lead to
418 bad tarfiles when their length was a multiple of 512. This
419 is tested as well.
420 """
421
Neal Norwitz0662f8a2004-07-20 21:54:18 +0000422 def _length(self, s):
423 blocks, remainder = divmod(len(s) + 1, 512)
424 if remainder:
425 blocks += 1
426 return blocks * 512
427
428 def _calc_size(self, name, link=None):
429 # initial tar header
430 count = 512
431
432 if len(name) > tarfile.LENGTH_NAME:
433 # gnu longname extended header + longname
434 count += 512
435 count += self._length(name)
436
437 if link is not None and len(link) > tarfile.LENGTH_LINK:
438 # gnu longlink extended header + longlink
439 count += 512
440 count += self._length(link)
441
442 return count
443
444 def _test(self, name, link=None):
445 tarinfo = tarfile.TarInfo(name)
446 if link:
447 tarinfo.linkname = link
448 tarinfo.type = tarfile.LNKTYPE
449
Georg Brandl25f58f62006-12-06 22:21:23 +0000450 tar = tarfile.open(tmpname(), "w")
451 tar.posix = False
452 tar.addfile(tarinfo)
Neal Norwitz0662f8a2004-07-20 21:54:18 +0000453
454 v1 = self._calc_size(name, link)
Georg Brandl25f58f62006-12-06 22:21:23 +0000455 v2 = tar.offset
Neal Norwitz0662f8a2004-07-20 21:54:18 +0000456 self.assertEqual(v1, v2, "GNU longname/longlink creation failed")
457
Georg Brandl25f58f62006-12-06 22:21:23 +0000458 tar.close()
459
460 tar = tarfile.open(tmpname())
461 member = tar.next()
462 self.failIf(member is None, "unable to read longname member")
463 self.assert_(tarinfo.name == member.name and \
464 tarinfo.linkname == member.linkname, \
465 "unable to read longname member")
466
Neal Norwitz0662f8a2004-07-20 21:54:18 +0000467 def test_longname_1023(self):
468 self._test(("longnam/" * 127) + "longnam")
469
470 def test_longname_1024(self):
471 self._test(("longnam/" * 127) + "longname")
472
473 def test_longname_1025(self):
474 self._test(("longnam/" * 127) + "longname_")
475
476 def test_longlink_1023(self):
477 self._test("name", ("longlnk/" * 127) + "longlnk")
478
479 def test_longlink_1024(self):
480 self._test("name", ("longlnk/" * 127) + "longlink")
481
482 def test_longlink_1025(self):
483 self._test("name", ("longlnk/" * 127) + "longlink_")
484
485 def test_longnamelink_1023(self):
486 self._test(("longnam/" * 127) + "longnam",
487 ("longlnk/" * 127) + "longlnk")
488
489 def test_longnamelink_1024(self):
490 self._test(("longnam/" * 127) + "longname",
491 ("longlnk/" * 127) + "longlink")
492
493 def test_longnamelink_1025(self):
494 self._test(("longnam/" * 127) + "longname_",
495 ("longlnk/" * 127) + "longlink_")
496
Georg Brandl38c6a222006-05-10 16:26:03 +0000497class ReadGNULongTest(unittest.TestCase):
498
499 def setUp(self):
500 self.tar = tarfile.open(tarname())
501
502 def tearDown(self):
503 self.tar.close()
504
505 def test_1471427(self):
506 """Test reading of longname (bug #1471427).
507 """
508 name = "test/" * 20 + "0-REGTYPE"
509 try:
510 tarinfo = self.tar.getmember(name)
511 except KeyError:
512 tarinfo = None
513 self.assert_(tarinfo is not None, "longname not found")
514 self.assert_(tarinfo.type != tarfile.DIRTYPE, "read longname as dirtype")
515
516 def test_read_name(self):
517 name = ("0-LONGNAME-" * 10)[:101]
518 try:
519 tarinfo = self.tar.getmember(name)
520 except KeyError:
521 tarinfo = None
522 self.assert_(tarinfo is not None, "longname not found")
523
524 def test_read_link(self):
525 link = ("1-LONGLINK-" * 10)[:101]
526 name = ("0-LONGNAME-" * 10)[:101]
527 try:
528 tarinfo = self.tar.getmember(link)
529 except KeyError:
530 tarinfo = None
531 self.assert_(tarinfo is not None, "longlink not found")
532 self.assert_(tarinfo.linkname == name, "linkname wrong")
533
534 def test_truncated_longname(self):
Tim Peters02494762006-05-26 14:02:05 +0000535 f = open(tarname())
536 fobj = StringIO.StringIO(f.read(1024))
537 f.close()
Georg Brandl38c6a222006-05-10 16:26:03 +0000538 tar = tarfile.open(name="foo.tar", fileobj=fobj)
539 self.assert_(len(tar.getmembers()) == 0, "")
Tim Peters02494762006-05-26 14:02:05 +0000540 tar.close()
Georg Brandl38c6a222006-05-10 16:26:03 +0000541
542
Neal Norwitza4f651a2004-07-20 22:07:44 +0000543class ExtractHardlinkTest(BaseTest):
544
545 def test_hardlink(self):
546 """Test hardlink extraction (bug #857297)
547 """
548 # Prevent errors from being caught
549 self.tar.errorlevel = 1
550
551 self.tar.extract("0-REGTYPE", dirname())
552 try:
553 # Extract 1-LNKTYPE which is a hardlink to 0-REGTYPE
554 self.tar.extract("1-LNKTYPE", dirname())
555 except EnvironmentError, e:
556 import errno
557 if e.errno == errno.ENOENT:
558 self.fail("hardlink not extracted properly")
559
Neal Norwitzb0e32e22005-10-20 04:50:13 +0000560class CreateHardlinkTest(BaseTest):
561 """Test the creation of LNKTYPE (hardlink) members in an archive.
562 In this respect tarfile.py mimics the behaviour of GNU tar: If
563 a file has a st_nlink > 1, it will be added a REGTYPE member
564 only the first time.
565 """
566
567 def setUp(self):
568 self.tar = tarfile.open(tmpname(), "w")
569
570 self.foo = os.path.join(dirname(), "foo")
571 self.bar = os.path.join(dirname(), "bar")
572
573 if os.path.exists(self.foo):
574 os.remove(self.foo)
575 if os.path.exists(self.bar):
576 os.remove(self.bar)
577
Tim Peters02494762006-05-26 14:02:05 +0000578 f = open(self.foo, "w")
579 f.write("foo")
580 f.close()
Neal Norwitzb0e32e22005-10-20 04:50:13 +0000581 self.tar.add(self.foo)
582
583 def test_add_twice(self):
584 # If st_nlink == 1 then the same file will be added as
585 # REGTYPE every time.
586 tarinfo = self.tar.gettarinfo(self.foo)
587 self.assertEqual(tarinfo.type, tarfile.REGTYPE,
588 "add file as regular failed")
589
590 def test_add_hardlink(self):
591 # If st_nlink > 1 then the same file will be added as
592 # LNKTYPE.
593 os.link(self.foo, self.bar)
594 tarinfo = self.tar.gettarinfo(self.foo)
595 self.assertEqual(tarinfo.type, tarfile.LNKTYPE,
596 "add file as hardlink failed")
597
598 tarinfo = self.tar.gettarinfo(self.bar)
599 self.assertEqual(tarinfo.type, tarfile.LNKTYPE,
600 "add file as hardlink failed")
601
602 def test_dereference_hardlink(self):
603 self.tar.dereference = True
604 os.link(self.foo, self.bar)
605 tarinfo = self.tar.gettarinfo(self.bar)
606 self.assertEqual(tarinfo.type, tarfile.REGTYPE,
607 "dereferencing hardlink failed")
608
Neal Norwitza4f651a2004-07-20 22:07:44 +0000609
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +0000610# Gzip TestCases
611class ReadTestGzip(ReadTest):
612 comp = "gz"
613class ReadStreamTestGzip(ReadStreamTest):
614 comp = "gz"
615class WriteTestGzip(WriteTest):
616 comp = "gz"
617class WriteStreamTestGzip(WriteStreamTest):
618 comp = "gz"
Georg Brandl49c8f4c2006-05-15 19:30:35 +0000619class ReadDetectTestGzip(ReadDetectTest):
620 comp = "gz"
621class ReadDetectFileobjTestGzip(ReadDetectFileobjTest):
622 comp = "gz"
Martin v. Löwis78be7df2005-03-05 12:47:42 +0000623class ReadAsteriskTestGzip(ReadAsteriskTest):
624 comp = "gz"
625class ReadStreamAsteriskTestGzip(ReadStreamAsteriskTest):
626 comp = "gz"
627
Andrew M. Kuchlingd4f25522004-10-20 11:47:01 +0000628# Filemode test cases
629
630class FileModeTest(unittest.TestCase):
631 def test_modes(self):
632 self.assertEqual(tarfile.filemode(0755), '-rwxr-xr-x')
633 self.assertEqual(tarfile.filemode(07111), '---s--s--t')
634
Lars Gustäbelf9a2c632006-12-27 10:36:58 +0000635class OpenFileobjTest(BaseTest):
Lars Gustäbelf9a2c632006-12-27 10:36:58 +0000636
637 def test_opener(self):
Lars Gustäbel9319e432007-04-20 20:10:59 +0000638 # Test for SF bug #1496501.
Lars Gustäbelf9a2c632006-12-27 10:36:58 +0000639 fobj = StringIO.StringIO("foo\n")
640 try:
Lars Gustäbel9319e432007-04-20 20:10:59 +0000641 tarfile.open("", mode="r", fileobj=fobj)
Lars Gustäbelf9a2c632006-12-27 10:36:58 +0000642 except tarfile.ReadError:
643 self.assertEqual(fobj.tell(), 0, "fileobj's position has moved")
Tim Peters8ceefc52004-10-25 03:19:41 +0000644
Lars Gustäbela9bad982007-08-28 12:33:15 +0000645 def test_no_name_argument(self):
646 fobj = open(testtar, "rb")
647 tar = tarfile.open(fileobj=fobj, mode="r")
648 self.assertEqual(tar.name, os.path.abspath(fobj.name))
649
650 def test_no_name_attribute(self):
651 data = open(testtar, "rb").read()
652 fobj = StringIO.StringIO(data)
653 self.assertRaises(AttributeError, getattr, fobj, "name")
654 tar = tarfile.open(fileobj=fobj, mode="r")
655 self.assertEqual(tar.name, None)
656
657 def test_empty_name_attribute(self):
658 data = open(testtar, "rb").read()
659 fobj = StringIO.StringIO(data)
660 fobj.name = ""
661 tar = tarfile.open(fileobj=fobj, mode="r")
662 self.assertEqual(tar.name, None)
663
Lars Gustäbel9319e432007-04-20 20:10:59 +0000664
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +0000665if bz2:
666 # Bzip2 TestCases
667 class ReadTestBzip2(ReadTestGzip):
668 comp = "bz2"
669 class ReadStreamTestBzip2(ReadStreamTestGzip):
670 comp = "bz2"
671 class WriteTestBzip2(WriteTest):
672 comp = "bz2"
673 class WriteStreamTestBzip2(WriteStreamTestGzip):
674 comp = "bz2"
Georg Brandl49c8f4c2006-05-15 19:30:35 +0000675 class ReadDetectTestBzip2(ReadDetectTest):
676 comp = "bz2"
677 class ReadDetectFileobjTestBzip2(ReadDetectFileobjTest):
678 comp = "bz2"
Martin v. Löwis78be7df2005-03-05 12:47:42 +0000679 class ReadAsteriskTestBzip2(ReadAsteriskTest):
680 comp = "bz2"
681 class ReadStreamAsteriskTestBzip2(ReadStreamAsteriskTest):
682 comp = "bz2"
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +0000683
684# If importing gzip failed, discard the Gzip TestCases.
685if not gzip:
686 del ReadTestGzip
687 del ReadStreamTestGzip
688 del WriteTestGzip
689 del WriteStreamTestGzip
690
Neal Norwitz996acf12003-02-17 14:51:41 +0000691def test_main():
Tim Peters02494762006-05-26 14:02:05 +0000692 # Create archive.
693 f = open(tarname(), "rb")
694 fguts = f.read()
695 f.close()
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +0000696 if gzip:
697 # create testtar.tar.gz
Tim Peters02494762006-05-26 14:02:05 +0000698 tar = gzip.open(tarname("gz"), "wb")
699 tar.write(fguts)
700 tar.close()
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +0000701 if bz2:
702 # create testtar.tar.bz2
Tim Peters02494762006-05-26 14:02:05 +0000703 tar = bz2.BZ2File(tarname("bz2"), "wb")
704 tar.write(fguts)
705 tar.close()
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +0000706
Walter Dörwald21d3a322003-05-01 17:45:56 +0000707 tests = [
Andrew M. Kuchlingd4f25522004-10-20 11:47:01 +0000708 FileModeTest,
Lars Gustäbelf9a2c632006-12-27 10:36:58 +0000709 OpenFileobjTest,
Walter Dörwald21d3a322003-05-01 17:45:56 +0000710 ReadTest,
711 ReadStreamTest,
Georg Brandl49c8f4c2006-05-15 19:30:35 +0000712 ReadDetectTest,
713 ReadDetectFileobjTest,
Martin v. Löwis78be7df2005-03-05 12:47:42 +0000714 ReadAsteriskTest,
715 ReadStreamAsteriskTest,
Walter Dörwald21d3a322003-05-01 17:45:56 +0000716 WriteTest,
Georg Brandlee23f4b2006-10-24 16:54:23 +0000717 Write100Test,
Martin v. Löwis5dbdc592005-08-27 10:07:56 +0000718 WriteSize0Test,
Neal Norwitz0662f8a2004-07-20 21:54:18 +0000719 WriteStreamTest,
720 WriteGNULongTest,
Georg Brandl38c6a222006-05-10 16:26:03 +0000721 ReadGNULongTest,
Walter Dörwald21d3a322003-05-01 17:45:56 +0000722 ]
723
Neal Norwitza4f651a2004-07-20 22:07:44 +0000724 if hasattr(os, "link"):
725 tests.append(ExtractHardlinkTest)
Neal Norwitzb0e32e22005-10-20 04:50:13 +0000726 tests.append(CreateHardlinkTest)
Neal Norwitza4f651a2004-07-20 22:07:44 +0000727
Walter Dörwald21d3a322003-05-01 17:45:56 +0000728 if gzip:
729 tests.extend([
730 ReadTestGzip, ReadStreamTestGzip,
Martin v. Löwis78be7df2005-03-05 12:47:42 +0000731 WriteTestGzip, WriteStreamTestGzip,
Georg Brandl49c8f4c2006-05-15 19:30:35 +0000732 ReadDetectTestGzip, ReadDetectFileobjTestGzip,
Martin v. Löwis78be7df2005-03-05 12:47:42 +0000733 ReadAsteriskTestGzip, ReadStreamAsteriskTestGzip
Walter Dörwald21d3a322003-05-01 17:45:56 +0000734 ])
735
736 if bz2:
737 tests.extend([
738 ReadTestBzip2, ReadStreamTestBzip2,
Martin v. Löwis78be7df2005-03-05 12:47:42 +0000739 WriteTestBzip2, WriteStreamTestBzip2,
Georg Brandl49c8f4c2006-05-15 19:30:35 +0000740 ReadDetectTestBzip2, ReadDetectFileobjTestBzip2,
Martin v. Löwis78be7df2005-03-05 12:47:42 +0000741 ReadAsteriskTestBzip2, ReadStreamAsteriskTestBzip2
Walter Dörwald21d3a322003-05-01 17:45:56 +0000742 ])
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +0000743 try:
Walter Dörwald21d3a322003-05-01 17:45:56 +0000744 test_support.run_unittest(*tests)
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +0000745 finally:
746 if gzip:
747 os.remove(tarname("gz"))
748 if bz2:
Tim Peters4e306172006-05-27 14:13:13 +0000749 os.remove(tarname("bz2"))
Brett Cannon455ea532003-06-12 08:01:06 +0000750 if os.path.exists(dirname()):
751 shutil.rmtree(dirname())
752 if os.path.exists(tmpname()):
753 os.remove(tmpname())
Neal Norwitzb9ef4ae2003-01-05 23:19:43 +0000754
Neal Norwitz996acf12003-02-17 14:51:41 +0000755if __name__ == "__main__":
756 test_main()