17db96d56Sopenharmony_ci"""Test script for the dbm.open function based on testdumbdbm.py""" 27db96d56Sopenharmony_ci 37db96d56Sopenharmony_ciimport unittest 47db96d56Sopenharmony_ciimport dbm 57db96d56Sopenharmony_ciimport os 67db96d56Sopenharmony_cifrom test.support import import_helper 77db96d56Sopenharmony_cifrom test.support import os_helper 87db96d56Sopenharmony_ci 97db96d56Sopenharmony_citry: 107db96d56Sopenharmony_ci from dbm import ndbm 117db96d56Sopenharmony_ciexcept ImportError: 127db96d56Sopenharmony_ci ndbm = None 137db96d56Sopenharmony_ci 147db96d56Sopenharmony_cidirname = os_helper.TESTFN 157db96d56Sopenharmony_ci_fname = os.path.join(dirname, os_helper.TESTFN) 167db96d56Sopenharmony_ci 177db96d56Sopenharmony_ci# 187db96d56Sopenharmony_ci# Iterates over every database module supported by dbm currently available. 197db96d56Sopenharmony_ci# 207db96d56Sopenharmony_cidef dbm_iterator(): 217db96d56Sopenharmony_ci for name in dbm._names: 227db96d56Sopenharmony_ci try: 237db96d56Sopenharmony_ci mod = __import__(name, fromlist=['open']) 247db96d56Sopenharmony_ci except ImportError: 257db96d56Sopenharmony_ci continue 267db96d56Sopenharmony_ci dbm._modules[name] = mod 277db96d56Sopenharmony_ci yield mod 287db96d56Sopenharmony_ci 297db96d56Sopenharmony_ci# 307db96d56Sopenharmony_ci# Clean up all scratch databases we might have created during testing 317db96d56Sopenharmony_ci# 327db96d56Sopenharmony_cidef cleaunup_test_dir(): 337db96d56Sopenharmony_ci os_helper.rmtree(dirname) 347db96d56Sopenharmony_ci 357db96d56Sopenharmony_cidef setup_test_dir(): 367db96d56Sopenharmony_ci cleaunup_test_dir() 377db96d56Sopenharmony_ci os.mkdir(dirname) 387db96d56Sopenharmony_ci 397db96d56Sopenharmony_ci 407db96d56Sopenharmony_ciclass AnyDBMTestCase: 417db96d56Sopenharmony_ci _dict = {'a': b'Python:', 427db96d56Sopenharmony_ci 'b': b'Programming', 437db96d56Sopenharmony_ci 'c': b'the', 447db96d56Sopenharmony_ci 'd': b'way', 457db96d56Sopenharmony_ci 'f': b'Guido', 467db96d56Sopenharmony_ci 'g': b'intended', 477db96d56Sopenharmony_ci } 487db96d56Sopenharmony_ci 497db96d56Sopenharmony_ci def init_db(self): 507db96d56Sopenharmony_ci f = dbm.open(_fname, 'n') 517db96d56Sopenharmony_ci for k in self._dict: 527db96d56Sopenharmony_ci f[k.encode("ascii")] = self._dict[k] 537db96d56Sopenharmony_ci f.close() 547db96d56Sopenharmony_ci 557db96d56Sopenharmony_ci def keys_helper(self, f): 567db96d56Sopenharmony_ci keys = sorted(k.decode("ascii") for k in f.keys()) 577db96d56Sopenharmony_ci dkeys = sorted(self._dict.keys()) 587db96d56Sopenharmony_ci self.assertEqual(keys, dkeys) 597db96d56Sopenharmony_ci return keys 607db96d56Sopenharmony_ci 617db96d56Sopenharmony_ci def test_error(self): 627db96d56Sopenharmony_ci self.assertTrue(issubclass(self.module.error, OSError)) 637db96d56Sopenharmony_ci 647db96d56Sopenharmony_ci def test_anydbm_not_existing(self): 657db96d56Sopenharmony_ci self.assertRaises(dbm.error, dbm.open, _fname) 667db96d56Sopenharmony_ci 677db96d56Sopenharmony_ci def test_anydbm_creation(self): 687db96d56Sopenharmony_ci f = dbm.open(_fname, 'c') 697db96d56Sopenharmony_ci self.assertEqual(list(f.keys()), []) 707db96d56Sopenharmony_ci for key in self._dict: 717db96d56Sopenharmony_ci f[key.encode("ascii")] = self._dict[key] 727db96d56Sopenharmony_ci self.read_helper(f) 737db96d56Sopenharmony_ci f.close() 747db96d56Sopenharmony_ci 757db96d56Sopenharmony_ci def test_anydbm_creation_n_file_exists_with_invalid_contents(self): 767db96d56Sopenharmony_ci # create an empty file 777db96d56Sopenharmony_ci os_helper.create_empty_file(_fname) 787db96d56Sopenharmony_ci with dbm.open(_fname, 'n') as f: 797db96d56Sopenharmony_ci self.assertEqual(len(f), 0) 807db96d56Sopenharmony_ci 817db96d56Sopenharmony_ci def test_anydbm_modification(self): 827db96d56Sopenharmony_ci self.init_db() 837db96d56Sopenharmony_ci f = dbm.open(_fname, 'c') 847db96d56Sopenharmony_ci self._dict['g'] = f[b'g'] = b"indented" 857db96d56Sopenharmony_ci self.read_helper(f) 867db96d56Sopenharmony_ci # setdefault() works as in the dict interface 877db96d56Sopenharmony_ci self.assertEqual(f.setdefault(b'xxx', b'foo'), b'foo') 887db96d56Sopenharmony_ci self.assertEqual(f[b'xxx'], b'foo') 897db96d56Sopenharmony_ci f.close() 907db96d56Sopenharmony_ci 917db96d56Sopenharmony_ci def test_anydbm_read(self): 927db96d56Sopenharmony_ci self.init_db() 937db96d56Sopenharmony_ci f = dbm.open(_fname, 'r') 947db96d56Sopenharmony_ci self.read_helper(f) 957db96d56Sopenharmony_ci # get() works as in the dict interface 967db96d56Sopenharmony_ci self.assertEqual(f.get(b'a'), self._dict['a']) 977db96d56Sopenharmony_ci self.assertEqual(f.get(b'xxx', b'foo'), b'foo') 987db96d56Sopenharmony_ci self.assertIsNone(f.get(b'xxx')) 997db96d56Sopenharmony_ci with self.assertRaises(KeyError): 1007db96d56Sopenharmony_ci f[b'xxx'] 1017db96d56Sopenharmony_ci f.close() 1027db96d56Sopenharmony_ci 1037db96d56Sopenharmony_ci def test_anydbm_keys(self): 1047db96d56Sopenharmony_ci self.init_db() 1057db96d56Sopenharmony_ci f = dbm.open(_fname, 'r') 1067db96d56Sopenharmony_ci keys = self.keys_helper(f) 1077db96d56Sopenharmony_ci f.close() 1087db96d56Sopenharmony_ci 1097db96d56Sopenharmony_ci def test_empty_value(self): 1107db96d56Sopenharmony_ci if getattr(dbm._defaultmod, 'library', None) == 'Berkeley DB': 1117db96d56Sopenharmony_ci self.skipTest("Berkeley DB doesn't distinguish the empty value " 1127db96d56Sopenharmony_ci "from the absent one") 1137db96d56Sopenharmony_ci f = dbm.open(_fname, 'c') 1147db96d56Sopenharmony_ci self.assertEqual(f.keys(), []) 1157db96d56Sopenharmony_ci f[b'empty'] = b'' 1167db96d56Sopenharmony_ci self.assertEqual(f.keys(), [b'empty']) 1177db96d56Sopenharmony_ci self.assertIn(b'empty', f) 1187db96d56Sopenharmony_ci self.assertEqual(f[b'empty'], b'') 1197db96d56Sopenharmony_ci self.assertEqual(f.get(b'empty'), b'') 1207db96d56Sopenharmony_ci self.assertEqual(f.setdefault(b'empty'), b'') 1217db96d56Sopenharmony_ci f.close() 1227db96d56Sopenharmony_ci 1237db96d56Sopenharmony_ci def test_anydbm_access(self): 1247db96d56Sopenharmony_ci self.init_db() 1257db96d56Sopenharmony_ci f = dbm.open(_fname, 'r') 1267db96d56Sopenharmony_ci key = "a".encode("ascii") 1277db96d56Sopenharmony_ci self.assertIn(key, f) 1287db96d56Sopenharmony_ci assert(f[key] == b"Python:") 1297db96d56Sopenharmony_ci f.close() 1307db96d56Sopenharmony_ci 1317db96d56Sopenharmony_ci def test_open_with_bytes(self): 1327db96d56Sopenharmony_ci dbm.open(os.fsencode(_fname), "c").close() 1337db96d56Sopenharmony_ci 1347db96d56Sopenharmony_ci def test_open_with_pathlib_path(self): 1357db96d56Sopenharmony_ci dbm.open(os_helper.FakePath(_fname), "c").close() 1367db96d56Sopenharmony_ci 1377db96d56Sopenharmony_ci def test_open_with_pathlib_path_bytes(self): 1387db96d56Sopenharmony_ci dbm.open(os_helper.FakePath(os.fsencode(_fname)), "c").close() 1397db96d56Sopenharmony_ci 1407db96d56Sopenharmony_ci def read_helper(self, f): 1417db96d56Sopenharmony_ci keys = self.keys_helper(f) 1427db96d56Sopenharmony_ci for key in self._dict: 1437db96d56Sopenharmony_ci self.assertEqual(self._dict[key], f[key.encode("ascii")]) 1447db96d56Sopenharmony_ci 1457db96d56Sopenharmony_ci def test_keys(self): 1467db96d56Sopenharmony_ci with dbm.open(_fname, 'c') as d: 1477db96d56Sopenharmony_ci self.assertEqual(d.keys(), []) 1487db96d56Sopenharmony_ci a = [(b'a', b'b'), (b'12345678910', b'019237410982340912840198242')] 1497db96d56Sopenharmony_ci for k, v in a: 1507db96d56Sopenharmony_ci d[k] = v 1517db96d56Sopenharmony_ci self.assertEqual(sorted(d.keys()), sorted(k for (k, v) in a)) 1527db96d56Sopenharmony_ci for k, v in a: 1537db96d56Sopenharmony_ci self.assertIn(k, d) 1547db96d56Sopenharmony_ci self.assertEqual(d[k], v) 1557db96d56Sopenharmony_ci self.assertNotIn(b'xxx', d) 1567db96d56Sopenharmony_ci self.assertRaises(KeyError, lambda: d[b'xxx']) 1577db96d56Sopenharmony_ci 1587db96d56Sopenharmony_ci def setUp(self): 1597db96d56Sopenharmony_ci self.addCleanup(setattr, dbm, '_defaultmod', dbm._defaultmod) 1607db96d56Sopenharmony_ci dbm._defaultmod = self.module 1617db96d56Sopenharmony_ci self.addCleanup(cleaunup_test_dir) 1627db96d56Sopenharmony_ci setup_test_dir() 1637db96d56Sopenharmony_ci 1647db96d56Sopenharmony_ci 1657db96d56Sopenharmony_ciclass WhichDBTestCase(unittest.TestCase): 1667db96d56Sopenharmony_ci def test_whichdb(self): 1677db96d56Sopenharmony_ci self.addCleanup(setattr, dbm, '_defaultmod', dbm._defaultmod) 1687db96d56Sopenharmony_ci _bytes_fname = os.fsencode(_fname) 1697db96d56Sopenharmony_ci fnames = [_fname, os_helper.FakePath(_fname), 1707db96d56Sopenharmony_ci _bytes_fname, os_helper.FakePath(_bytes_fname)] 1717db96d56Sopenharmony_ci for module in dbm_iterator(): 1727db96d56Sopenharmony_ci # Check whether whichdb correctly guesses module name 1737db96d56Sopenharmony_ci # for databases opened with "module" module. 1747db96d56Sopenharmony_ci name = module.__name__ 1757db96d56Sopenharmony_ci setup_test_dir() 1767db96d56Sopenharmony_ci dbm._defaultmod = module 1777db96d56Sopenharmony_ci # Try with empty files first 1787db96d56Sopenharmony_ci with module.open(_fname, 'c'): pass 1797db96d56Sopenharmony_ci for path in fnames: 1807db96d56Sopenharmony_ci self.assertEqual(name, self.dbm.whichdb(path)) 1817db96d56Sopenharmony_ci # Now add a key 1827db96d56Sopenharmony_ci with module.open(_fname, 'w') as f: 1837db96d56Sopenharmony_ci f[b"1"] = b"1" 1847db96d56Sopenharmony_ci # and test that we can find it 1857db96d56Sopenharmony_ci self.assertIn(b"1", f) 1867db96d56Sopenharmony_ci # and read it 1877db96d56Sopenharmony_ci self.assertEqual(f[b"1"], b"1") 1887db96d56Sopenharmony_ci for path in fnames: 1897db96d56Sopenharmony_ci self.assertEqual(name, self.dbm.whichdb(path)) 1907db96d56Sopenharmony_ci 1917db96d56Sopenharmony_ci @unittest.skipUnless(ndbm, reason='Test requires ndbm') 1927db96d56Sopenharmony_ci def test_whichdb_ndbm(self): 1937db96d56Sopenharmony_ci # Issue 17198: check that ndbm which is referenced in whichdb is defined 1947db96d56Sopenharmony_ci with open(_fname + '.db', 'wb'): pass 1957db96d56Sopenharmony_ci _bytes_fname = os.fsencode(_fname) 1967db96d56Sopenharmony_ci fnames = [_fname, os_helper.FakePath(_fname), 1977db96d56Sopenharmony_ci _bytes_fname, os_helper.FakePath(_bytes_fname)] 1987db96d56Sopenharmony_ci for path in fnames: 1997db96d56Sopenharmony_ci self.assertIsNone(self.dbm.whichdb(path)) 2007db96d56Sopenharmony_ci 2017db96d56Sopenharmony_ci def setUp(self): 2027db96d56Sopenharmony_ci self.addCleanup(cleaunup_test_dir) 2037db96d56Sopenharmony_ci setup_test_dir() 2047db96d56Sopenharmony_ci self.dbm = import_helper.import_fresh_module('dbm') 2057db96d56Sopenharmony_ci 2067db96d56Sopenharmony_ci 2077db96d56Sopenharmony_cifor mod in dbm_iterator(): 2087db96d56Sopenharmony_ci assert mod.__name__.startswith('dbm.') 2097db96d56Sopenharmony_ci suffix = mod.__name__[4:] 2107db96d56Sopenharmony_ci testname = f'TestCase_{suffix}' 2117db96d56Sopenharmony_ci globals()[testname] = type(testname, 2127db96d56Sopenharmony_ci (AnyDBMTestCase, unittest.TestCase), 2137db96d56Sopenharmony_ci {'module': mod}) 2147db96d56Sopenharmony_ci 2157db96d56Sopenharmony_ci 2167db96d56Sopenharmony_ciif __name__ == "__main__": 2177db96d56Sopenharmony_ci unittest.main() 218