blob: a35821000d04dc4ac9159c2e82ed3ee19e98e7f9 [file] [log] [blame]
Guido van Rossum0e548712002-08-09 16:14:33 +00001# tempfile.py unit tests.
Tim Petersc57a2852001-10-29 21:46:08 +00002import tempfile
Guido van Rossum0e548712002-08-09 16:14:33 +00003import os
4import sys
5import re
6import errno
7import warnings
Tim Petersc57a2852001-10-29 21:46:08 +00008
Guido van Rossum0e548712002-08-09 16:14:33 +00009import unittest
10from test import test_support
11
Fred Drake7633d232002-10-17 22:09:03 +000012warnings.filterwarnings("ignore",
13 category=RuntimeWarning,
14 message="mktemp", module=__name__)
15
Guido van Rossum0e548712002-08-09 16:14:33 +000016if hasattr(os, 'stat'):
17 import stat
18 has_stat = 1
19else:
20 has_stat = 0
21
22has_textmode = (tempfile._text_openflags != tempfile._bin_openflags)
Guido van Rossum78741062002-08-17 11:41:01 +000023has_spawnl = hasattr(os, 'spawnl')
Guido van Rossum0e548712002-08-09 16:14:33 +000024
Neal Norwitz68ee0122002-08-16 19:28:59 +000025# TEST_FILES may need to be tweaked for systems depending on the maximum
26# number of files that can be opened at one time (see ulimit -n)
Jack Jansence921472003-01-08 16:30:34 +000027if sys.platform == 'mac':
28 TEST_FILES = 32
Neal Norwitz4bc2c092006-09-05 02:57:01 +000029elif sys.platform in ('openbsd3', 'openbsd4'):
Martin v. Löwis99968282004-09-15 06:02:54 +000030 TEST_FILES = 48
Jack Jansence921472003-01-08 16:30:34 +000031else:
32 TEST_FILES = 100
Neal Norwitz68ee0122002-08-16 19:28:59 +000033
Guido van Rossum0e548712002-08-09 16:14:33 +000034# This is organized as one test for each chunk of code in tempfile.py,
35# in order of their appearance in the file. Testing which requires
36# threads is not done here.
37
38# Common functionality.
39class TC(unittest.TestCase):
40
41 str_check = re.compile(r"[a-zA-Z0-9_-]{6}$")
42
43 def failOnException(self, what, ei=None):
44 if ei is None:
45 ei = sys.exc_info()
46 self.fail("%s raised %s: %s" % (what, ei[0], ei[1]))
47
48 def nameCheck(self, name, dir, pre, suf):
49 (ndir, nbase) = os.path.split(name)
50 npre = nbase[:len(pre)]
51 nsuf = nbase[len(nbase)-len(suf):]
52
Martin v. Löwisd6625482003-10-12 17:37:01 +000053 # check for equality of the absolute paths!
54 self.assertEqual(os.path.abspath(ndir), os.path.abspath(dir),
Guido van Rossum0e548712002-08-09 16:14:33 +000055 "file '%s' not in directory '%s'" % (name, dir))
56 self.assertEqual(npre, pre,
57 "file '%s' does not begin with '%s'" % (nbase, pre))
58 self.assertEqual(nsuf, suf,
59 "file '%s' does not end with '%s'" % (nbase, suf))
60
61 nbase = nbase[len(pre):len(nbase)-len(suf)]
Benjamin Peterson5c8da862009-06-30 22:57:08 +000062 self.assertTrue(self.str_check.match(nbase),
Guido van Rossum0e548712002-08-09 16:14:33 +000063 "random string '%s' does not match /^[a-zA-Z0-9_-]{6}$/"
64 % nbase)
65
66test_classes = []
67
68class test_exports(TC):
69 def test_exports(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +000070 # There are no surprising symbols in the tempfile module
Guido van Rossum0e548712002-08-09 16:14:33 +000071 dict = tempfile.__dict__
72
73 expected = {
74 "NamedTemporaryFile" : 1,
75 "TemporaryFile" : 1,
76 "mkstemp" : 1,
77 "mkdtemp" : 1,
78 "mktemp" : 1,
79 "TMP_MAX" : 1,
80 "gettempprefix" : 1,
81 "gettempdir" : 1,
82 "tempdir" : 1,
Collin Wintera8785cc2007-03-19 18:52:08 +000083 "template" : 1,
84 "SpooledTemporaryFile" : 1
Guido van Rossum0e548712002-08-09 16:14:33 +000085 }
86
87 unexp = []
88 for key in dict:
89 if key[0] != '_' and key not in expected:
90 unexp.append(key)
Benjamin Peterson5c8da862009-06-30 22:57:08 +000091 self.assertTrue(len(unexp) == 0,
Guido van Rossum0e548712002-08-09 16:14:33 +000092 "unexpected keys: %s" % unexp)
93
94test_classes.append(test_exports)
95
96
Guido van Rossum0e548712002-08-09 16:14:33 +000097class test__RandomNameSequence(TC):
98 """Test the internal iterator object _RandomNameSequence."""
99
100 def setUp(self):
101 self.r = tempfile._RandomNameSequence()
102
103 def test_get_six_char_str(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000104 # _RandomNameSequence returns a six-character string
Guido van Rossum0e548712002-08-09 16:14:33 +0000105 s = self.r.next()
106 self.nameCheck(s, '', '', '')
107
108 def test_many(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000109 # _RandomNameSequence returns no duplicate strings (stochastic)
Guido van Rossum0e548712002-08-09 16:14:33 +0000110
111 dict = {}
112 r = self.r
Neal Norwitz68ee0122002-08-16 19:28:59 +0000113 for i in xrange(TEST_FILES):
Guido van Rossum0e548712002-08-09 16:14:33 +0000114 s = r.next()
115 self.nameCheck(s, '', '', '')
Ezio Melottiaa980582010-01-23 23:04:36 +0000116 self.assertNotIn(s, dict)
Guido van Rossum0e548712002-08-09 16:14:33 +0000117 dict[s] = 1
118
119 def test_supports_iter(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000120 # _RandomNameSequence supports the iterator protocol
Guido van Rossum0e548712002-08-09 16:14:33 +0000121
122 i = 0
123 r = self.r
124 try:
125 for s in r:
126 i += 1
127 if i == 20:
128 break
129 except:
130 failOnException("iteration")
131
132test_classes.append(test__RandomNameSequence)
133
134
135class test__candidate_tempdir_list(TC):
136 """Test the internal function _candidate_tempdir_list."""
137
138 def test_nonempty_list(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000139 # _candidate_tempdir_list returns a nonempty list of strings
Guido van Rossum0e548712002-08-09 16:14:33 +0000140
141 cand = tempfile._candidate_tempdir_list()
142
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000143 self.assertFalse(len(cand) == 0)
Guido van Rossum0e548712002-08-09 16:14:33 +0000144 for c in cand:
Ezio Melottib0f5adc2010-01-24 16:58:36 +0000145 self.assertIsInstance(c, basestring)
Guido van Rossum0e548712002-08-09 16:14:33 +0000146
147 def test_wanted_dirs(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000148 # _candidate_tempdir_list contains the expected directories
Guido van Rossum0e548712002-08-09 16:14:33 +0000149
150 # Make sure the interesting environment variables are all set.
Walter Dörwald4b965f62009-04-26 20:51:44 +0000151 with test_support.EnvironmentVarGuard() as env:
Guido van Rossum0e548712002-08-09 16:14:33 +0000152 for envname in 'TMPDIR', 'TEMP', 'TMP':
153 dirname = os.getenv(envname)
154 if not dirname:
Walter Dörwald6733bed2009-05-01 17:35:37 +0000155 env[envname] = os.path.abspath(envname)
Guido van Rossum0e548712002-08-09 16:14:33 +0000156
157 cand = tempfile._candidate_tempdir_list()
158
159 for envname in 'TMPDIR', 'TEMP', 'TMP':
160 dirname = os.getenv(envname)
161 if not dirname: raise ValueError
Ezio Melottiaa980582010-01-23 23:04:36 +0000162 self.assertIn(dirname, cand)
Guido van Rossum0e548712002-08-09 16:14:33 +0000163
164 try:
165 dirname = os.getcwd()
166 except (AttributeError, os.error):
167 dirname = os.curdir
168
Ezio Melottiaa980582010-01-23 23:04:36 +0000169 self.assertIn(dirname, cand)
Guido van Rossum0e548712002-08-09 16:14:33 +0000170
171 # Not practical to try to verify the presence of OS-specific
172 # paths in this list.
Guido van Rossum0e548712002-08-09 16:14:33 +0000173
174test_classes.append(test__candidate_tempdir_list)
175
176
177# We test _get_default_tempdir by testing gettempdir.
178
179
180class test__get_candidate_names(TC):
181 """Test the internal function _get_candidate_names."""
182
183 def test_retval(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000184 # _get_candidate_names returns a _RandomNameSequence object
Guido van Rossum0e548712002-08-09 16:14:33 +0000185 obj = tempfile._get_candidate_names()
Ezio Melottib0f5adc2010-01-24 16:58:36 +0000186 self.assertIsInstance(obj, tempfile._RandomNameSequence)
Guido van Rossum0e548712002-08-09 16:14:33 +0000187
188 def test_same_thing(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000189 # _get_candidate_names always returns the same object
Guido van Rossum0e548712002-08-09 16:14:33 +0000190 a = tempfile._get_candidate_names()
191 b = tempfile._get_candidate_names()
192
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000193 self.assertTrue(a is b)
Guido van Rossum0e548712002-08-09 16:14:33 +0000194
195test_classes.append(test__get_candidate_names)
196
197
198class test__mkstemp_inner(TC):
199 """Test the internal function _mkstemp_inner."""
200
201 class mkstemped:
202 _bflags = tempfile._bin_openflags
203 _tflags = tempfile._text_openflags
204 _close = os.close
205 _unlink = os.unlink
206
207 def __init__(self, dir, pre, suf, bin):
208 if bin: flags = self._bflags
209 else: flags = self._tflags
210
211 (self.fd, self.name) = tempfile._mkstemp_inner(dir, pre, suf, flags)
212
213 def write(self, str):
214 os.write(self.fd, str)
215
216 def __del__(self):
217 self._close(self.fd)
218 self._unlink(self.name)
Tim Petersa0d55de2002-08-09 18:01:01 +0000219
Guido van Rossum0e548712002-08-09 16:14:33 +0000220 def do_create(self, dir=None, pre="", suf="", bin=1):
221 if dir is None:
222 dir = tempfile.gettempdir()
223 try:
224 file = self.mkstemped(dir, pre, suf, bin)
225 except:
226 self.failOnException("_mkstemp_inner")
227
228 self.nameCheck(file.name, dir, pre, suf)
229 return file
230
231 def test_basic(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000232 # _mkstemp_inner can create files
Guido van Rossum0e548712002-08-09 16:14:33 +0000233 self.do_create().write("blat")
234 self.do_create(pre="a").write("blat")
235 self.do_create(suf="b").write("blat")
236 self.do_create(pre="a", suf="b").write("blat")
237 self.do_create(pre="aa", suf=".txt").write("blat")
238
239 def test_basic_many(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000240 # _mkstemp_inner can create many files (stochastic)
Neal Norwitz68ee0122002-08-16 19:28:59 +0000241 extant = range(TEST_FILES)
Guido van Rossum0e548712002-08-09 16:14:33 +0000242 for i in extant:
243 extant[i] = self.do_create(pre="aa")
244
245 def test_choose_directory(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000246 # _mkstemp_inner can create files in a user-selected directory
Guido van Rossum0e548712002-08-09 16:14:33 +0000247 dir = tempfile.mkdtemp()
248 try:
249 self.do_create(dir=dir).write("blat")
250 finally:
251 os.rmdir(dir)
252
253 def test_file_mode(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000254 # _mkstemp_inner creates files with the proper mode
Guido van Rossum0e548712002-08-09 16:14:33 +0000255 if not has_stat:
Benjamin Peterson888a39b2009-03-26 20:48:25 +0000256 return # ugh, can't use SkipTest.
Guido van Rossum0e548712002-08-09 16:14:33 +0000257
258 file = self.do_create()
259 mode = stat.S_IMODE(os.stat(file.name).st_mode)
Tim Petersca3ac7f2002-08-09 18:13:51 +0000260 expected = 0600
Jack Jansence921472003-01-08 16:30:34 +0000261 if sys.platform in ('win32', 'os2emx', 'mac'):
Tim Petersca3ac7f2002-08-09 18:13:51 +0000262 # There's no distinction among 'user', 'group' and 'world';
263 # replicate the 'user' bits.
264 user = expected >> 6
265 expected = user * (1 + 8 + 64)
266 self.assertEqual(mode, expected)
Guido van Rossum0e548712002-08-09 16:14:33 +0000267
268 def test_noinherit(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000269 # _mkstemp_inner file handles are not inherited by child processes
Guido van Rossum78741062002-08-17 11:41:01 +0000270 if not has_spawnl:
Benjamin Peterson888a39b2009-03-26 20:48:25 +0000271 return # ugh, can't use SkipTest.
Guido van Rossum0e548712002-08-09 16:14:33 +0000272
Guido van Rossum78741062002-08-17 11:41:01 +0000273 if test_support.verbose:
274 v="v"
275 else:
276 v="q"
277
Guido van Rossum0e548712002-08-09 16:14:33 +0000278 file = self.do_create()
Guido van Rossum78741062002-08-17 11:41:01 +0000279 fd = "%d" % file.fd
280
281 try:
282 me = __file__
283 except NameError:
284 me = sys.argv[0]
Guido van Rossum0e548712002-08-09 16:14:33 +0000285
286 # We have to exec something, so that FD_CLOEXEC will take
Guido van Rossum78741062002-08-17 11:41:01 +0000287 # effect. The core of this test is therefore in
288 # tf_inherit_check.py, which see.
289 tester = os.path.join(os.path.dirname(os.path.abspath(me)),
290 "tf_inherit_check.py")
Guido van Rossum0e548712002-08-09 16:14:33 +0000291
Martin v. Löwisd4210bc2003-10-23 15:55:28 +0000292 # On Windows a spawn* /path/ with embedded spaces shouldn't be quoted,
293 # but an arg with embedded spaces should be decorated with double
294 # quotes on each end
Armin Rigo66d41b22007-12-07 19:19:55 +0000295 if sys.platform in ('win32',):
Martin v. Löwisd4210bc2003-10-23 15:55:28 +0000296 decorated = '"%s"' % sys.executable
297 tester = '"%s"' % tester
298 else:
299 decorated = sys.executable
300
301 retval = os.spawnl(os.P_WAIT, sys.executable, decorated, tester, v, fd)
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000302 self.assertFalse(retval < 0,
Guido van Rossum78741062002-08-17 11:41:01 +0000303 "child process caught fatal signal %d" % -retval)
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000304 self.assertFalse(retval > 0, "child process reports failure %d"%retval)
Guido van Rossum0e548712002-08-09 16:14:33 +0000305
306 def test_textmode(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000307 # _mkstemp_inner can create files in text mode
Guido van Rossum0e548712002-08-09 16:14:33 +0000308 if not has_textmode:
Benjamin Peterson888a39b2009-03-26 20:48:25 +0000309 return # ugh, can't use SkipTest.
Guido van Rossum0e548712002-08-09 16:14:33 +0000310
311 self.do_create(bin=0).write("blat\n")
312 # XXX should test that the file really is a text file
313
314test_classes.append(test__mkstemp_inner)
315
316
317class test_gettempprefix(TC):
318 """Test gettempprefix()."""
319
320 def test_sane_template(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000321 # gettempprefix returns a nonempty prefix string
Guido van Rossum0e548712002-08-09 16:14:33 +0000322 p = tempfile.gettempprefix()
323
Ezio Melottib0f5adc2010-01-24 16:58:36 +0000324 self.assertIsInstance(p, basestring)
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000325 self.assertTrue(len(p) > 0)
Guido van Rossum0e548712002-08-09 16:14:33 +0000326
327 def test_usable_template(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000328 # gettempprefix returns a usable prefix string
Guido van Rossum0e548712002-08-09 16:14:33 +0000329
330 # Create a temp directory, avoiding use of the prefix.
331 # Then attempt to create a file whose name is
332 # prefix + 'xxxxxx.xxx' in that directory.
333 p = tempfile.gettempprefix() + "xxxxxx.xxx"
334 d = tempfile.mkdtemp(prefix="")
335 try:
336 p = os.path.join(d, p)
337 try:
338 fd = os.open(p, os.O_RDWR | os.O_CREAT)
339 except:
340 self.failOnException("os.open")
341 os.close(fd)
342 os.unlink(p)
343 finally:
344 os.rmdir(d)
345
346test_classes.append(test_gettempprefix)
347
348
349class test_gettempdir(TC):
350 """Test gettempdir()."""
351
352 def test_directory_exists(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000353 # gettempdir returns a directory which exists
Guido van Rossum0e548712002-08-09 16:14:33 +0000354
355 dir = tempfile.gettempdir()
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000356 self.assertTrue(os.path.isabs(dir) or dir == os.curdir,
Guido van Rossum0e548712002-08-09 16:14:33 +0000357 "%s is not an absolute path" % dir)
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000358 self.assertTrue(os.path.isdir(dir),
Guido van Rossum0e548712002-08-09 16:14:33 +0000359 "%s is not a directory" % dir)
360
361 def test_directory_writable(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000362 # gettempdir returns a directory writable by the user
Guido van Rossum0e548712002-08-09 16:14:33 +0000363
364 # sneaky: just instantiate a NamedTemporaryFile, which
365 # defaults to writing into the directory returned by
366 # gettempdir.
367 try:
368 file = tempfile.NamedTemporaryFile()
369 file.write("blat")
370 file.close()
371 except:
372 self.failOnException("create file in %s" % tempfile.gettempdir())
373
374 def test_same_thing(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000375 # gettempdir always returns the same object
Guido van Rossum0e548712002-08-09 16:14:33 +0000376 a = tempfile.gettempdir()
377 b = tempfile.gettempdir()
378
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000379 self.assertTrue(a is b)
Guido van Rossum0e548712002-08-09 16:14:33 +0000380
381test_classes.append(test_gettempdir)
382
383
384class test_mkstemp(TC):
385 """Test mkstemp()."""
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000386
Martin Blais215f13d2006-06-06 12:46:55 +0000387 def do_create(self, dir=None, pre="", suf=""):
Guido van Rossum0e548712002-08-09 16:14:33 +0000388 if dir is None:
389 dir = tempfile.gettempdir()
390 try:
391 (fd, name) = tempfile.mkstemp(dir=dir, prefix=pre, suffix=suf)
Martin v. Löwisd6625482003-10-12 17:37:01 +0000392 (ndir, nbase) = os.path.split(name)
393 adir = os.path.abspath(dir)
394 self.assertEqual(adir, ndir,
395 "Directory '%s' incorrectly returned as '%s'" % (adir, ndir))
Guido van Rossum0e548712002-08-09 16:14:33 +0000396 except:
397 self.failOnException("mkstemp")
398
399 try:
400 self.nameCheck(name, dir, pre, suf)
401 finally:
402 os.close(fd)
403 os.unlink(name)
404
405 def test_basic(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000406 # mkstemp can create files
Guido van Rossum0e548712002-08-09 16:14:33 +0000407 self.do_create()
408 self.do_create(pre="a")
409 self.do_create(suf="b")
410 self.do_create(pre="a", suf="b")
411 self.do_create(pre="aa", suf=".txt")
Martin v. Löwisd6625482003-10-12 17:37:01 +0000412 self.do_create(dir=".")
Guido van Rossum0e548712002-08-09 16:14:33 +0000413
414 def test_choose_directory(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000415 # mkstemp can create directories in a user-selected directory
Guido van Rossum0e548712002-08-09 16:14:33 +0000416 dir = tempfile.mkdtemp()
417 try:
418 self.do_create(dir=dir)
419 finally:
420 os.rmdir(dir)
421
422test_classes.append(test_mkstemp)
423
424
425class test_mkdtemp(TC):
426 """Test mkdtemp()."""
427
428 def do_create(self, dir=None, pre="", suf=""):
429 if dir is None:
430 dir = tempfile.gettempdir()
431 try:
432 name = tempfile.mkdtemp(dir=dir, prefix=pre, suffix=suf)
433 except:
434 self.failOnException("mkdtemp")
435
436 try:
437 self.nameCheck(name, dir, pre, suf)
438 return name
439 except:
440 os.rmdir(name)
441 raise
442
443 def test_basic(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000444 # mkdtemp can create directories
Guido van Rossum0e548712002-08-09 16:14:33 +0000445 os.rmdir(self.do_create())
446 os.rmdir(self.do_create(pre="a"))
447 os.rmdir(self.do_create(suf="b"))
448 os.rmdir(self.do_create(pre="a", suf="b"))
449 os.rmdir(self.do_create(pre="aa", suf=".txt"))
Tim Petersa0d55de2002-08-09 18:01:01 +0000450
Guido van Rossum0e548712002-08-09 16:14:33 +0000451 def test_basic_many(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000452 # mkdtemp can create many directories (stochastic)
Neal Norwitz68ee0122002-08-16 19:28:59 +0000453 extant = range(TEST_FILES)
Guido van Rossum0e548712002-08-09 16:14:33 +0000454 try:
455 for i in extant:
456 extant[i] = self.do_create(pre="aa")
457 finally:
458 for i in extant:
459 if(isinstance(i, basestring)):
460 os.rmdir(i)
461
462 def test_choose_directory(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000463 # mkdtemp can create directories in a user-selected directory
Guido van Rossum0e548712002-08-09 16:14:33 +0000464 dir = tempfile.mkdtemp()
465 try:
466 os.rmdir(self.do_create(dir=dir))
467 finally:
468 os.rmdir(dir)
469
470 def test_mode(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000471 # mkdtemp creates directories with the proper mode
Guido van Rossum0e548712002-08-09 16:14:33 +0000472 if not has_stat:
Benjamin Peterson888a39b2009-03-26 20:48:25 +0000473 return # ugh, can't use SkipTest.
Guido van Rossum0e548712002-08-09 16:14:33 +0000474
475 dir = self.do_create()
476 try:
477 mode = stat.S_IMODE(os.stat(dir).st_mode)
Guido van Rossum59db96f2004-03-31 18:53:29 +0000478 mode &= 0777 # Mask off sticky bits inherited from /tmp
Tim Petersca3ac7f2002-08-09 18:13:51 +0000479 expected = 0700
Jack Jansence921472003-01-08 16:30:34 +0000480 if sys.platform in ('win32', 'os2emx', 'mac'):
Tim Petersca3ac7f2002-08-09 18:13:51 +0000481 # There's no distinction among 'user', 'group' and 'world';
482 # replicate the 'user' bits.
483 user = expected >> 6
484 expected = user * (1 + 8 + 64)
485 self.assertEqual(mode, expected)
Guido van Rossum0e548712002-08-09 16:14:33 +0000486 finally:
487 os.rmdir(dir)
488
489test_classes.append(test_mkdtemp)
490
491
492class test_mktemp(TC):
493 """Test mktemp()."""
494
495 # For safety, all use of mktemp must occur in a private directory.
496 # We must also suppress the RuntimeWarning it generates.
497 def setUp(self):
498 self.dir = tempfile.mkdtemp()
Guido van Rossum0e548712002-08-09 16:14:33 +0000499
500 def tearDown(self):
501 if self.dir:
502 os.rmdir(self.dir)
503 self.dir = None
Guido van Rossum0e548712002-08-09 16:14:33 +0000504
505 class mktemped:
506 _unlink = os.unlink
507 _bflags = tempfile._bin_openflags
508
509 def __init__(self, dir, pre, suf):
510 self.name = tempfile.mktemp(dir=dir, prefix=pre, suffix=suf)
511 # Create the file. This will raise an exception if it's
512 # mysteriously appeared in the meanwhile.
513 os.close(os.open(self.name, self._bflags, 0600))
514
515 def __del__(self):
516 self._unlink(self.name)
517
518 def do_create(self, pre="", suf=""):
519 try:
520 file = self.mktemped(self.dir, pre, suf)
521 except:
522 self.failOnException("mktemp")
523
524 self.nameCheck(file.name, self.dir, pre, suf)
525 return file
526
527 def test_basic(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000528 # mktemp can choose usable file names
Guido van Rossum0e548712002-08-09 16:14:33 +0000529 self.do_create()
530 self.do_create(pre="a")
531 self.do_create(suf="b")
532 self.do_create(pre="a", suf="b")
533 self.do_create(pre="aa", suf=".txt")
534
535 def test_many(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000536 # mktemp can choose many usable file names (stochastic)
Neal Norwitz68ee0122002-08-16 19:28:59 +0000537 extant = range(TEST_FILES)
Guido van Rossum0e548712002-08-09 16:14:33 +0000538 for i in extant:
539 extant[i] = self.do_create(pre="aa")
540
Fred Drake8bec4832002-11-22 20:13:43 +0000541## def test_warning(self):
542## # mktemp issues a warning when used
543## warnings.filterwarnings("error",
544## category=RuntimeWarning,
545## message="mktemp")
546## self.assertRaises(RuntimeWarning,
547## tempfile.mktemp, dir=self.dir)
Guido van Rossum0e548712002-08-09 16:14:33 +0000548
549test_classes.append(test_mktemp)
550
551
552# We test _TemporaryFileWrapper by testing NamedTemporaryFile.
553
554
555class test_NamedTemporaryFile(TC):
556 """Test NamedTemporaryFile()."""
557
Georg Brandl35ef9c12007-03-13 18:31:49 +0000558 def do_create(self, dir=None, pre="", suf="", delete=True):
Guido van Rossum0e548712002-08-09 16:14:33 +0000559 if dir is None:
560 dir = tempfile.gettempdir()
561 try:
Georg Brandl35ef9c12007-03-13 18:31:49 +0000562 file = tempfile.NamedTemporaryFile(dir=dir, prefix=pre, suffix=suf,
Georg Brandl4168c042007-03-13 19:18:18 +0000563 delete=delete)
Guido van Rossum0e548712002-08-09 16:14:33 +0000564 except:
565 self.failOnException("NamedTemporaryFile")
566
567 self.nameCheck(file.name, dir, pre, suf)
568 return file
569
570
571 def test_basic(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000572 # NamedTemporaryFile can create files
Guido van Rossum0e548712002-08-09 16:14:33 +0000573 self.do_create()
574 self.do_create(pre="a")
575 self.do_create(suf="b")
576 self.do_create(pre="a", suf="b")
577 self.do_create(pre="aa", suf=".txt")
578
579 def test_creates_named(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000580 # NamedTemporaryFile creates files with names
Guido van Rossum0e548712002-08-09 16:14:33 +0000581 f = tempfile.NamedTemporaryFile()
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000582 self.assertTrue(os.path.exists(f.name),
Guido van Rossum0e548712002-08-09 16:14:33 +0000583 "NamedTemporaryFile %s does not exist" % f.name)
584
585 def test_del_on_close(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000586 # A NamedTemporaryFile is deleted when closed
Guido van Rossum0e548712002-08-09 16:14:33 +0000587 dir = tempfile.mkdtemp()
588 try:
589 f = tempfile.NamedTemporaryFile(dir=dir)
590 f.write('blat')
591 f.close()
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000592 self.assertFalse(os.path.exists(f.name),
Guido van Rossum0e548712002-08-09 16:14:33 +0000593 "NamedTemporaryFile %s exists after close" % f.name)
594 finally:
595 os.rmdir(dir)
596
Georg Brandl35ef9c12007-03-13 18:31:49 +0000597 def test_dis_del_on_close(self):
598 # Tests that delete-on-close can be disabled
599 dir = tempfile.mkdtemp()
Georg Brandl4168c042007-03-13 19:18:18 +0000600 tmp = None
Georg Brandl35ef9c12007-03-13 18:31:49 +0000601 try:
602 f = tempfile.NamedTemporaryFile(dir=dir, delete=False)
603 tmp = f.name
604 f.write('blat')
605 f.close()
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000606 self.assertTrue(os.path.exists(f.name),
Georg Brandl35ef9c12007-03-13 18:31:49 +0000607 "NamedTemporaryFile %s missing after close" % f.name)
608 finally:
609 if tmp is not None:
610 os.unlink(tmp)
611 os.rmdir(dir)
612
Guido van Rossum0e548712002-08-09 16:14:33 +0000613 def test_multiple_close(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000614 # A NamedTemporaryFile can be closed many times without error
Guido van Rossum0e548712002-08-09 16:14:33 +0000615 f = tempfile.NamedTemporaryFile()
616 f.write('abc\n')
617 f.close()
618 try:
619 f.close()
620 f.close()
621 except:
622 self.failOnException("close")
623
Nick Coghlan97fac3e2008-02-09 15:28:09 +0000624 def test_context_manager(self):
625 # A NamedTemporaryFile can be used as a context manager
626 with tempfile.NamedTemporaryFile() as f:
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000627 self.assertTrue(os.path.exists(f.name))
628 self.assertFalse(os.path.exists(f.name))
Nick Coghlan97fac3e2008-02-09 15:28:09 +0000629 def use_closed():
630 with f:
631 pass
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000632 self.assertRaises(ValueError, use_closed)
Nick Coghlan97fac3e2008-02-09 15:28:09 +0000633
Guido van Rossum0e548712002-08-09 16:14:33 +0000634 # How to test the mode and bufsize parameters?
635
636test_classes.append(test_NamedTemporaryFile)
637
Collin Wintera8785cc2007-03-19 18:52:08 +0000638class test_SpooledTemporaryFile(TC):
639 """Test SpooledTemporaryFile()."""
640
641 def do_create(self, max_size=0, dir=None, pre="", suf=""):
642 if dir is None:
643 dir = tempfile.gettempdir()
644 try:
645 file = tempfile.SpooledTemporaryFile(max_size=max_size, dir=dir, prefix=pre, suffix=suf)
646 except:
647 self.failOnException("SpooledTemporaryFile")
648
649 return file
650
651
652 def test_basic(self):
653 # SpooledTemporaryFile can create files
654 f = self.do_create()
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000655 self.assertFalse(f._rolled)
Collin Wintera8785cc2007-03-19 18:52:08 +0000656 f = self.do_create(max_size=100, pre="a", suf=".txt")
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000657 self.assertFalse(f._rolled)
Collin Wintera8785cc2007-03-19 18:52:08 +0000658
659 def test_del_on_close(self):
660 # A SpooledTemporaryFile is deleted when closed
661 dir = tempfile.mkdtemp()
662 try:
663 f = tempfile.SpooledTemporaryFile(max_size=10, dir=dir)
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000664 self.assertFalse(f._rolled)
Collin Wintera8785cc2007-03-19 18:52:08 +0000665 f.write('blat ' * 5)
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000666 self.assertTrue(f._rolled)
Collin Wintera8785cc2007-03-19 18:52:08 +0000667 filename = f.name
668 f.close()
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000669 self.assertFalse(os.path.exists(filename),
Collin Wintera8785cc2007-03-19 18:52:08 +0000670 "SpooledTemporaryFile %s exists after close" % filename)
671 finally:
672 os.rmdir(dir)
673
674 def test_rewrite_small(self):
675 # A SpooledTemporaryFile can be written to multiple within the max_size
676 f = self.do_create(max_size=30)
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000677 self.assertFalse(f._rolled)
Collin Wintera8785cc2007-03-19 18:52:08 +0000678 for i in range(5):
679 f.seek(0, 0)
680 f.write('x' * 20)
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000681 self.assertFalse(f._rolled)
Collin Wintera8785cc2007-03-19 18:52:08 +0000682
683 def test_write_sequential(self):
684 # A SpooledTemporaryFile should hold exactly max_size bytes, and roll
685 # over afterward
686 f = self.do_create(max_size=30)
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000687 self.assertFalse(f._rolled)
Collin Wintera8785cc2007-03-19 18:52:08 +0000688 f.write('x' * 20)
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000689 self.assertFalse(f._rolled)
Collin Wintera8785cc2007-03-19 18:52:08 +0000690 f.write('x' * 10)
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000691 self.assertFalse(f._rolled)
Collin Wintera8785cc2007-03-19 18:52:08 +0000692 f.write('x')
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000693 self.assertTrue(f._rolled)
Collin Wintera8785cc2007-03-19 18:52:08 +0000694
695 def test_sparse(self):
696 # A SpooledTemporaryFile that is written late in the file will extend
697 # when that occurs
698 f = self.do_create(max_size=30)
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000699 self.assertFalse(f._rolled)
Collin Wintera8785cc2007-03-19 18:52:08 +0000700 f.seek(100, 0)
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000701 self.assertFalse(f._rolled)
Collin Wintera8785cc2007-03-19 18:52:08 +0000702 f.write('x')
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000703 self.assertTrue(f._rolled)
Collin Wintera8785cc2007-03-19 18:52:08 +0000704
705 def test_fileno(self):
706 # A SpooledTemporaryFile should roll over to a real file on fileno()
707 f = self.do_create(max_size=30)
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000708 self.assertFalse(f._rolled)
709 self.assertTrue(f.fileno() > 0)
710 self.assertTrue(f._rolled)
Collin Wintera8785cc2007-03-19 18:52:08 +0000711
Nick Coghlan97fac3e2008-02-09 15:28:09 +0000712 def test_multiple_close_before_rollover(self):
Collin Wintera8785cc2007-03-19 18:52:08 +0000713 # A SpooledTemporaryFile can be closed many times without error
714 f = tempfile.SpooledTemporaryFile()
715 f.write('abc\n')
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000716 self.assertFalse(f._rolled)
Nick Coghlan97fac3e2008-02-09 15:28:09 +0000717 f.close()
718 try:
719 f.close()
720 f.close()
721 except:
722 self.failOnException("close")
723
724 def test_multiple_close_after_rollover(self):
725 # A SpooledTemporaryFile can be closed many times without error
726 f = tempfile.SpooledTemporaryFile(max_size=1)
727 f.write('abc\n')
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000728 self.assertTrue(f._rolled)
Collin Wintera8785cc2007-03-19 18:52:08 +0000729 f.close()
730 try:
731 f.close()
732 f.close()
733 except:
734 self.failOnException("close")
735
736 def test_bound_methods(self):
737 # It should be OK to steal a bound method from a SpooledTemporaryFile
738 # and use it independently; when the file rolls over, those bound
739 # methods should continue to function
740 f = self.do_create(max_size=30)
741 read = f.read
742 write = f.write
743 seek = f.seek
744
745 write("a" * 35)
746 write("b" * 35)
747 seek(0, 0)
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000748 self.assertTrue(read(70) == 'a'*35 + 'b'*35)
Collin Wintera8785cc2007-03-19 18:52:08 +0000749
Nick Coghlan97fac3e2008-02-09 15:28:09 +0000750 def test_context_manager_before_rollover(self):
751 # A SpooledTemporaryFile can be used as a context manager
752 with tempfile.SpooledTemporaryFile(max_size=1) as f:
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000753 self.assertFalse(f._rolled)
754 self.assertFalse(f.closed)
755 self.assertTrue(f.closed)
Nick Coghlan97fac3e2008-02-09 15:28:09 +0000756 def use_closed():
757 with f:
758 pass
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000759 self.assertRaises(ValueError, use_closed)
Nick Coghlan97fac3e2008-02-09 15:28:09 +0000760
761 def test_context_manager_during_rollover(self):
762 # A SpooledTemporaryFile can be used as a context manager
763 with tempfile.SpooledTemporaryFile(max_size=1) as f:
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000764 self.assertFalse(f._rolled)
Nick Coghlan97fac3e2008-02-09 15:28:09 +0000765 f.write('abc\n')
766 f.flush()
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000767 self.assertTrue(f._rolled)
768 self.assertFalse(f.closed)
769 self.assertTrue(f.closed)
Nick Coghlan97fac3e2008-02-09 15:28:09 +0000770 def use_closed():
771 with f:
772 pass
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000773 self.assertRaises(ValueError, use_closed)
Nick Coghlan97fac3e2008-02-09 15:28:09 +0000774
775 def test_context_manager_after_rollover(self):
776 # A SpooledTemporaryFile can be used as a context manager
777 f = tempfile.SpooledTemporaryFile(max_size=1)
778 f.write('abc\n')
779 f.flush()
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000780 self.assertTrue(f._rolled)
Nick Coghlan97fac3e2008-02-09 15:28:09 +0000781 with f:
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000782 self.assertFalse(f.closed)
783 self.assertTrue(f.closed)
Nick Coghlan97fac3e2008-02-09 15:28:09 +0000784 def use_closed():
785 with f:
786 pass
Benjamin Peterson5c8da862009-06-30 22:57:08 +0000787 self.assertRaises(ValueError, use_closed)
Nick Coghlan97fac3e2008-02-09 15:28:09 +0000788
789
Collin Wintera8785cc2007-03-19 18:52:08 +0000790test_classes.append(test_SpooledTemporaryFile)
791
Guido van Rossum0e548712002-08-09 16:14:33 +0000792
793class test_TemporaryFile(TC):
794 """Test TemporaryFile()."""
795
796 def test_basic(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000797 # TemporaryFile can create files
Guido van Rossum0e548712002-08-09 16:14:33 +0000798 # No point in testing the name params - the file has no name.
799 try:
800 tempfile.TemporaryFile()
801 except:
802 self.failOnException("TemporaryFile")
803
804 def test_has_no_name(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000805 # TemporaryFile creates files with no names (on this system)
Guido van Rossum0e548712002-08-09 16:14:33 +0000806 dir = tempfile.mkdtemp()
807 f = tempfile.TemporaryFile(dir=dir)
808 f.write('blat')
809
810 # Sneaky: because this file has no name, it should not prevent
811 # us from removing the directory it was created in.
812 try:
813 os.rmdir(dir)
814 except:
815 ei = sys.exc_info()
816 # cleanup
817 f.close()
818 os.rmdir(dir)
819 self.failOnException("rmdir", ei)
820
821 def test_multiple_close(self):
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000822 # A TemporaryFile can be closed many times without error
Guido van Rossum0e548712002-08-09 16:14:33 +0000823 f = tempfile.TemporaryFile()
824 f.write('abc\n')
825 f.close()
826 try:
827 f.close()
828 f.close()
829 except:
830 self.failOnException("close")
831
832 # How to test the mode and bufsize parameters?
833
Guido van Rossum0e548712002-08-09 16:14:33 +0000834
Guido van Rossum8ccd9b62002-08-22 20:02:03 +0000835if tempfile.NamedTemporaryFile is not tempfile.TemporaryFile:
Guido van Rossum0e548712002-08-09 16:14:33 +0000836 test_classes.append(test_TemporaryFile)
837
838def test_main():
Walter Dörwald21d3a322003-05-01 17:45:56 +0000839 test_support.run_unittest(*test_classes)
Guido van Rossum0e548712002-08-09 16:14:33 +0000840
841if __name__ == "__main__":
842 test_main()