test_support.py revision ef8b654bbea15dc55767a7095e01dff7a3ca86cb
1"""Supporting definitions for the Python regression test.""" 2 3import sys 4 5 6class Error(Exception): 7 """Base class for regression test exceptions.""" 8 9class TestFailed(Error): 10 """Test failed.""" 11 12class TestSkipped(Error): 13 """Test skipped. 14 15 This can be raised to indicate that a test was deliberatly 16 skipped, but not because a feature wasn't available. For 17 example, if some resource can't be used, such as the network 18 appears to be unavailable, this should be raised instead of 19 TestFailed. 20 """ 21 22verbose = 1 # Flag set to 0 by regrtest.py 23use_large_resources = 1 # Flag set to 0 by regrtest.py 24 25def unload(name): 26 try: 27 del sys.modules[name] 28 except KeyError: 29 pass 30 31def forget(modname): 32 unload(modname) 33 import os 34 for dirname in sys.path: 35 try: 36 os.unlink(os.path.join(dirname, modname + '.pyc')) 37 except os.error: 38 pass 39 40FUZZ = 1e-6 41 42def fcmp(x, y): # fuzzy comparison function 43 if type(x) == type(0.0) or type(y) == type(0.0): 44 try: 45 x, y = coerce(x, y) 46 fuzz = (abs(x) + abs(y)) * FUZZ 47 if abs(x-y) <= fuzz: 48 return 0 49 except: 50 pass 51 elif type(x) == type(y) and type(x) in (type(()), type([])): 52 for i in range(min(len(x), len(y))): 53 outcome = fcmp(x[i], y[i]) 54 if outcome != 0: 55 return outcome 56 return cmp(len(x), len(y)) 57 return cmp(x, y) 58 59import os 60# Filename used for testing 61if os.name == 'java': 62 # Jython disallows @ in module names 63 TESTFN = '$test' 64elif os.name != 'riscos': 65 TESTFN = '@test' 66 # Unicode name only used if TEST_FN_ENCODING exists for the platform. 67 TESTFN_UNICODE=u"@test-\xe0\xf2" # 2 latin characters. 68 if os.name=="nt": 69 TESTFN_ENCODING="mbcs" 70else: 71 TESTFN = 'test' 72del os 73 74from os import unlink 75 76def findfile(file, here=__file__): 77 import os 78 if os.path.isabs(file): 79 return file 80 path = sys.path 81 path = [os.path.dirname(here)] + path 82 for dn in path: 83 fn = os.path.join(dn, file) 84 if os.path.exists(fn): return fn 85 return file 86 87def verify(condition, reason='test failed'): 88 """Verify that condition is true. If not, raise TestFailed. 89 90 The optional argument reason can be given to provide 91 a better error text. 92 """ 93 94 if not condition: 95 raise TestFailed(reason) 96 97def sortdict(dict): 98 "Like repr(dict), but in sorted order." 99 items = dict.items() 100 items.sort() 101 reprpairs = ["%r: %r" % pair for pair in items] 102 withcommas = ", ".join(reprpairs) 103 return "{%s}" % withcommas 104 105def check_syntax(statement): 106 try: 107 compile(statement, '<string>', 'exec') 108 except SyntaxError: 109 pass 110 else: 111 print 'Missing SyntaxError: "%s"' % statement 112 113 114 115#======================================================================= 116# Preliminary PyUNIT integration. 117 118import unittest 119 120 121class BasicTestRunner: 122 def run(self, test): 123 result = unittest.TestResult() 124 test(result) 125 return result 126 127 128def run_unittest(testclass): 129 """Run tests from a unittest.TestCase-derived class.""" 130 if verbose: 131 runner = unittest.TextTestRunner(sys.stdout, verbosity=2) 132 else: 133 runner = BasicTestRunner() 134 135 suite = unittest.makeSuite(testclass) 136 result = runner.run(suite) 137 if not result.wasSuccessful(): 138 raise TestFailed("errors occurred in %s.%s" 139 % (testclass.__module__, testclass.__name__)) 140