blob: 6b981c429dfbf8fc62bbdbb5547fcd4c77b594bf [file] [log] [blame]
Benjamin Peterson90f5ba52010-03-11 22:53:45 +00001#! /usr/bin/env python3
Guido van Rossum2f1064c2001-01-18 16:46:52 +00002"""Test script for the dumbdbm module
3 Original by Roger E. Masse
4"""
5
Guido van Rossum6252e102007-05-23 20:51:02 +00006import io
Guido van Rossum2f1064c2001-01-18 16:46:52 +00007import os
Barry Warsaw3ca656f2001-11-13 20:16:52 +00008import unittest
Georg Brandl0a7ac7d2008-05-26 10:29:35 +00009import dbm.dumb as dumbdbm
Benjamin Petersonee8712c2008-05-20 21:35:26 +000010from test import support
Guido van Rossum2f1064c2001-01-18 16:46:52 +000011
Benjamin Petersonee8712c2008-05-20 21:35:26 +000012_fname = support.TESTFN
Tim Petersd9fbf352002-01-30 07:32:53 +000013
14def _delete_files():
15 for ext in [".dir", ".dat", ".bak"]:
16 try:
17 os.unlink(_fname + ext)
18 except OSError:
19 pass
20
Barry Warsaw3ca656f2001-11-13 20:16:52 +000021class DumbDBMTestCase(unittest.TestCase):
Brett Cannon58425d32008-11-21 00:17:53 +000022 _dict = {b'0': b'',
23 b'a': b'Python:',
24 b'b': b'Programming',
25 b'c': b'the',
26 b'd': b'way',
27 b'f': b'Guido',
28 b'g': b'intended',
29 '\u00fc'.encode('utf-8') : b'!',
Barry Warsaw3ca656f2001-11-13 20:16:52 +000030 }
31
32 def __init__(self, *args):
33 unittest.TestCase.__init__(self, *args)
Tim Peters88768482001-11-13 21:51:26 +000034
Barry Warsaw3ca656f2001-11-13 20:16:52 +000035 def test_dumbdbm_creation(self):
Tim Petersd9fbf352002-01-30 07:32:53 +000036 f = dumbdbm.open(_fname, 'c')
Brett Cannonc1b22a02007-02-22 05:04:32 +000037 self.assertEqual(list(f.keys()), [])
Barry Warsaw3ca656f2001-11-13 20:16:52 +000038 for key in self._dict:
Brett Cannon58425d32008-11-21 00:17:53 +000039 f[key] = self._dict[key]
Barry Warsaw3ca656f2001-11-13 20:16:52 +000040 self.read_helper(f)
41 f.close()
42
Thomas Wouters902d6eb2007-01-09 23:18:33 +000043 def test_dumbdbm_creation_mode(self):
44 # On platforms without chmod, don't do anything.
45 if not (hasattr(os, 'chmod') and hasattr(os, 'umask')):
46 return
47
48 try:
Guido van Rossumcd16bf62007-06-13 18:07:49 +000049 old_umask = os.umask(0o002)
50 f = dumbdbm.open(_fname, 'c', 0o637)
Thomas Wouters902d6eb2007-01-09 23:18:33 +000051 f.close()
52 finally:
53 os.umask(old_umask)
Thomas Wouters9fe394c2007-02-05 01:24:16 +000054
Guido van Rossumcd16bf62007-06-13 18:07:49 +000055 expected_mode = 0o635
Thomas Woutersb2137042007-02-01 18:02:27 +000056 if os.name != 'posix':
57 # Windows only supports setting the read-only attribute.
58 # This shouldn't fail, but doesn't work like Unix either.
Guido van Rossumcd16bf62007-06-13 18:07:49 +000059 expected_mode = 0o666
Thomas Woutersb2137042007-02-01 18:02:27 +000060
Thomas Wouters902d6eb2007-01-09 23:18:33 +000061 import stat
62 st = os.stat(_fname + '.dat')
Thomas Woutersb2137042007-02-01 18:02:27 +000063 self.assertEqual(stat.S_IMODE(st.st_mode), expected_mode)
Thomas Wouters902d6eb2007-01-09 23:18:33 +000064 st = os.stat(_fname + '.dir')
Thomas Woutersb2137042007-02-01 18:02:27 +000065 self.assertEqual(stat.S_IMODE(st.st_mode), expected_mode)
Thomas Wouters9fe394c2007-02-05 01:24:16 +000066
Tim Peters7a6c7332003-07-13 17:21:10 +000067 def test_close_twice(self):
68 f = dumbdbm.open(_fname)
Martin v. Löwise6568692007-08-07 05:37:39 +000069 f[b'a'] = b'b'
70 self.assertEqual(f[b'a'], b'b')
Tim Peters7a6c7332003-07-13 17:21:10 +000071 f.close()
72 f.close()
73
Barry Warsaw3ca656f2001-11-13 20:16:52 +000074 def test_dumbdbm_modification(self):
Skip Montanaroc08fe822002-03-17 23:03:42 +000075 self.init_db()
Tim Petersd9fbf352002-01-30 07:32:53 +000076 f = dumbdbm.open(_fname, 'w')
Brett Cannon58425d32008-11-21 00:17:53 +000077 self._dict[b'g'] = f[b'g'] = b"indented"
Barry Warsaw3ca656f2001-11-13 20:16:52 +000078 self.read_helper(f)
79 f.close()
80
81 def test_dumbdbm_read(self):
Skip Montanaroc08fe822002-03-17 23:03:42 +000082 self.init_db()
Tim Petersd9fbf352002-01-30 07:32:53 +000083 f = dumbdbm.open(_fname, 'r')
Barry Warsaw3ca656f2001-11-13 20:16:52 +000084 self.read_helper(f)
85 f.close()
86
87 def test_dumbdbm_keys(self):
Skip Montanaroc08fe822002-03-17 23:03:42 +000088 self.init_db()
Tim Petersd9fbf352002-01-30 07:32:53 +000089 f = dumbdbm.open(_fname)
Barry Warsaw3ca656f2001-11-13 20:16:52 +000090 keys = self.keys_helper(f)
91 f.close()
92
Gregory P. Smith178fefb2007-08-24 21:59:45 +000093 def test_write_contains(self):
94 f = dumbdbm.open(_fname)
95 f[b'1'] = b'hello'
Benjamin Peterson577473f2010-01-19 00:09:57 +000096 self.assertIn(b'1', f)
Gregory P. Smith178fefb2007-08-24 21:59:45 +000097 f.close()
98
Skip Montanaroc08fe822002-03-17 23:03:42 +000099 def test_write_write_read(self):
100 # test for bug #482460
101 f = dumbdbm.open(_fname)
Martin v. Löwise6568692007-08-07 05:37:39 +0000102 f[b'1'] = b'hello'
103 f[b'1'] = b'hello2'
Skip Montanaroc08fe822002-03-17 23:03:42 +0000104 f.close()
105 f = dumbdbm.open(_fname)
Guido van Rossum7b4beea2007-08-28 00:09:54 +0000106 self.assertEqual(f[b'1'], b'hello2')
Skip Montanaroc08fe822002-03-17 23:03:42 +0000107 f.close()
108
Brett Cannon58425d32008-11-21 00:17:53 +0000109 def test_str_read(self):
110 self.init_db()
111 f = dumbdbm.open(_fname, 'r')
112 self.assertEqual(f['\u00fc'], self._dict['\u00fc'.encode('utf-8')])
113
114 def test_str_write_contains(self):
115 self.init_db()
116 f = dumbdbm.open(_fname)
117 f['\u00fc'] = b'!'
Brett Cannon7317c1e2008-11-25 19:19:17 +0000118 f['1'] = 'a'
Brett Cannon58425d32008-11-21 00:17:53 +0000119 f.close()
120 f = dumbdbm.open(_fname, 'r')
Benjamin Peterson577473f2010-01-19 00:09:57 +0000121 self.assertIn('\u00fc', f)
Brett Cannon58425d32008-11-21 00:17:53 +0000122 self.assertEqual(f['\u00fc'.encode('utf-8')],
123 self._dict['\u00fc'.encode('utf-8')])
Brett Cannon7317c1e2008-11-25 19:19:17 +0000124 self.assertEqual(f[b'1'], b'a')
Brett Cannon58425d32008-11-21 00:17:53 +0000125
Andrew M. Kuchlingecdad852005-06-07 19:36:10 +0000126 def test_line_endings(self):
127 # test for bug #1172763: dumbdbm would die if the line endings
128 # weren't what was expected.
129 f = dumbdbm.open(_fname)
Martin v. Löwise6568692007-08-07 05:37:39 +0000130 f[b'1'] = b'hello'
131 f[b'2'] = b'hello2'
Andrew M. Kuchlingecdad852005-06-07 19:36:10 +0000132 f.close()
133
Christian Heimes9289bfc2007-10-31 19:40:17 +0000134 # Mangle the file by changing the line separator to Windows or Unix
Brett Cannonc0eee312010-10-29 22:49:14 +0000135 with io.open(_fname + '.dir', 'rb') as file:
136 data = file.read()
Guido van Rossum98297ee2007-11-06 21:34:58 +0000137 if os.linesep == '\n':
Christian Heimes9289bfc2007-10-31 19:40:17 +0000138 data = data.replace(b'\n', b'\r\n')
139 else:
140 data = data.replace(b'\r\n', b'\n')
Brett Cannonc0eee312010-10-29 22:49:14 +0000141 with io.open(_fname + '.dir', 'wb') as file:
142 file.write(data)
Anthony Baxter95a2a4e2005-06-08 04:35:50 +0000143
Andrew M. Kuchlingecdad852005-06-07 19:36:10 +0000144 f = dumbdbm.open(_fname)
Martin v. Löwise6568692007-08-07 05:37:39 +0000145 self.assertEqual(f[b'1'], b'hello')
146 self.assertEqual(f[b'2'], b'hello2')
Anthony Baxter95a2a4e2005-06-08 04:35:50 +0000147
148
Barry Warsaw3ca656f2001-11-13 20:16:52 +0000149 def read_helper(self, f):
150 keys = self.keys_helper(f)
151 for key in self._dict:
Brett Cannon58425d32008-11-21 00:17:53 +0000152 self.assertEqual(self._dict[key], f[key])
Tim Peters88768482001-11-13 21:51:26 +0000153
Skip Montanaroc08fe822002-03-17 23:03:42 +0000154 def init_db(self):
155 f = dumbdbm.open(_fname, 'w')
156 for k in self._dict:
Brett Cannon58425d32008-11-21 00:17:53 +0000157 f[k] = self._dict[k]
Skip Montanaroc08fe822002-03-17 23:03:42 +0000158 f.close()
159
Barry Warsaw3ca656f2001-11-13 20:16:52 +0000160 def keys_helper(self, f):
Brett Cannon58425d32008-11-21 00:17:53 +0000161 keys = sorted(f.keys())
Brett Cannonc1b22a02007-02-22 05:04:32 +0000162 dkeys = sorted(self._dict.keys())
Skip Montanaroc08fe822002-03-17 23:03:42 +0000163 self.assertEqual(keys, dkeys)
Barry Warsaw3ca656f2001-11-13 20:16:52 +0000164 return keys
165
Tim Peters663d1b62003-07-11 04:09:09 +0000166 # Perform randomized operations. This doesn't make assumptions about
167 # what *might* fail.
168 def test_random(self):
169 import random
170 d = {} # mirror the database
171 for dummy in range(5):
172 f = dumbdbm.open(_fname)
173 for dummy in range(100):
174 k = random.choice('abcdefghijklm')
175 if random.random() < 0.2:
176 if k in d:
177 del d[k]
Brett Cannon58425d32008-11-21 00:17:53 +0000178 del f[k]
Tim Peters663d1b62003-07-11 04:09:09 +0000179 else:
Guido van Rossum6252e102007-05-23 20:51:02 +0000180 v = random.choice((b'a', b'b', b'c')) * random.randrange(10000)
Tim Peters663d1b62003-07-11 04:09:09 +0000181 d[k] = v
Brett Cannon58425d32008-11-21 00:17:53 +0000182 f[k] = v
183 self.assertEqual(f[k], v)
Tim Peters663d1b62003-07-11 04:09:09 +0000184 f.close()
185
186 f = dumbdbm.open(_fname)
Guido van Rossum7b4beea2007-08-28 00:09:54 +0000187 expected = sorted((k.encode("latin-1"), v) for k, v in d.items())
Brett Cannonc1b22a02007-02-22 05:04:32 +0000188 got = sorted(f.items())
Tim Peters663d1b62003-07-11 04:09:09 +0000189 self.assertEqual(expected, got)
190 f.close()
191
Skip Montanaroc08fe822002-03-17 23:03:42 +0000192 def tearDown(self):
193 _delete_files()
194
195 def setUp(self):
196 _delete_files()
197
Barry Warsaw3ca656f2001-11-13 20:16:52 +0000198def test_main():
Tim Petersd9fbf352002-01-30 07:32:53 +0000199 try:
Benjamin Petersonee8712c2008-05-20 21:35:26 +0000200 support.run_unittest(DumbDBMTestCase)
Tim Petersd9fbf352002-01-30 07:32:53 +0000201 finally:
202 _delete_files()
Barry Warsaw3ca656f2001-11-13 20:16:52 +0000203
204if __name__ == "__main__":
205 test_main()