blob: 8afb84513590f4c2c61545ef9deb742680a9e88a [file] [log] [blame]
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001"""Test case implementation"""
2
3import sys
4import functools
5import difflib
Antoine Pitrou0715b9f2013-09-14 19:45:47 +02006import logging
Benjamin Petersonbed7d042009-07-19 21:01:52 +00007import pprint
8import re
9import warnings
Raymond Hettinger6e165b32010-11-27 09:31:37 +000010import collections
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +010011import contextlib
Antoine Pitrou96810222014-04-29 01:23:50 +020012import traceback
Benjamin Petersonbed7d042009-07-19 21:01:52 +000013
Benjamin Peterson847a4112010-03-14 15:04:17 +000014from . import result
Florent Xiclunac53ae582011-11-04 08:25:54 +010015from .util import (strclass, safe_repr, _count_diff_all_purpose,
Serhiy Storchaka77622f52013-09-23 23:07:00 +030016 _count_diff_hashable, _common_shorten_repr)
Benjamin Petersonbed7d042009-07-19 21:01:52 +000017
Benjamin Petersondccc1fc2010-03-22 00:15:53 +000018__unittest = True
Benjamin Petersonbed7d042009-07-19 21:01:52 +000019
Berker Peksag16ea19f2016-09-21 19:34:15 +030020_subtest_msg_sentinel = object()
Michael Foord9dad32e2010-06-05 13:49:56 +000021
22DIFF_OMITTED = ('\nDiff is %s characters long. '
23 'Set self.maxDiff to None to see it.')
24
Benjamin Petersonbed7d042009-07-19 21:01:52 +000025class SkipTest(Exception):
26 """
27 Raise this exception in a test to skip it.
28
Ezio Melotti265281a2013-03-27 20:11:55 +020029 Usually you can use TestCase.skipTest() or one of the skipping decorators
Benjamin Petersonbed7d042009-07-19 21:01:52 +000030 instead of raising this directly.
31 """
Benjamin Petersonbed7d042009-07-19 21:01:52 +000032
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +010033class _ShouldStop(Exception):
Benjamin Petersonbed7d042009-07-19 21:01:52 +000034 """
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +010035 The test should stop.
Benjamin Petersonbed7d042009-07-19 21:01:52 +000036 """
37
Benjamin Petersonbed7d042009-07-19 21:01:52 +000038class _UnexpectedSuccess(Exception):
39 """
40 The test was supposed to fail, but it didn't!
41 """
Michael Foordb3468f72010-12-19 03:19:47 +000042
43
44class _Outcome(object):
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +010045 def __init__(self, result=None):
46 self.expecting_failure = False
47 self.result = result
48 self.result_supports_subtests = hasattr(result, "addSubTest")
Michael Foordb3468f72010-12-19 03:19:47 +000049 self.success = True
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +010050 self.skipped = []
Michael Foordb3468f72010-12-19 03:19:47 +000051 self.expectedFailure = None
52 self.errors = []
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +010053
54 @contextlib.contextmanager
55 def testPartExecutor(self, test_case, isTest=False):
56 old_success = self.success
57 self.success = True
58 try:
59 yield
60 except KeyboardInterrupt:
61 raise
62 except SkipTest as e:
63 self.success = False
64 self.skipped.append((test_case, str(e)))
65 except _ShouldStop:
66 pass
67 except:
68 exc_info = sys.exc_info()
69 if self.expecting_failure:
70 self.expectedFailure = exc_info
71 else:
72 self.success = False
73 self.errors.append((test_case, exc_info))
Victor Stinner031bd532013-12-09 01:52:50 +010074 # explicitly break a reference cycle:
75 # exc_info -> frame -> exc_info
76 exc_info = None
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +010077 else:
78 if self.result_supports_subtests and self.success:
79 self.errors.append((test_case, None))
80 finally:
81 self.success = self.success and old_success
Michael Foordb3468f72010-12-19 03:19:47 +000082
Benjamin Petersonbed7d042009-07-19 21:01:52 +000083
84def _id(obj):
85 return obj
86
Lisa Roach0f221d02018-11-08 18:34:33 -080087
88_module_cleanups = []
Serhiy Storchaka2085bd02019-06-01 11:00:15 +030089def addModuleCleanup(function, /, *args, **kwargs):
Lisa Roach0f221d02018-11-08 18:34:33 -080090 """Same as addCleanup, except the cleanup items are called even if
91 setUpModule fails (unlike tearDownModule)."""
92 _module_cleanups.append((function, args, kwargs))
93
94
95def doModuleCleanups():
96 """Execute all module cleanup functions. Normally called for you after
97 tearDownModule."""
98 exceptions = []
99 while _module_cleanups:
100 function, args, kwargs = _module_cleanups.pop()
101 try:
102 function(*args, **kwargs)
103 except Exception as exc:
104 exceptions.append(exc)
105 if exceptions:
106 # Swallows all but first exception. If a multi-exception handler
107 # gets written we should use that here instead.
108 raise exceptions[0]
109
110
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000111def skip(reason):
112 """
113 Unconditionally skip a test.
114 """
115 def decorator(test_item):
Antoine Pitroub05ac862012-04-25 14:56:46 +0200116 if not isinstance(test_item, type):
Benjamin Peterson847a4112010-03-14 15:04:17 +0000117 @functools.wraps(test_item)
118 def skip_wrapper(*args, **kwargs):
119 raise SkipTest(reason)
120 test_item = skip_wrapper
121
122 test_item.__unittest_skip__ = True
123 test_item.__unittest_skip_why__ = reason
124 return test_item
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000125 return decorator
126
127def skipIf(condition, reason):
128 """
129 Skip a test if the condition is true.
130 """
131 if condition:
132 return skip(reason)
133 return _id
134
135def skipUnless(condition, reason):
136 """
137 Skip a test unless the condition is true.
138 """
139 if not condition:
140 return skip(reason)
141 return _id
142
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100143def expectedFailure(test_item):
144 test_item.__unittest_expecting_failure__ = True
145 return test_item
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000146
Serhiy Storchaka041dd8e2015-05-21 20:15:40 +0300147def _is_subtype(expected, basetype):
148 if isinstance(expected, tuple):
149 return all(_is_subtype(e, basetype) for e in expected)
150 return isinstance(expected, type) and issubclass(expected, basetype)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000151
Antoine Pitrou0715b9f2013-09-14 19:45:47 +0200152class _BaseTestCaseContext:
153
154 def __init__(self, test_case):
155 self.test_case = test_case
156
157 def _raiseFailure(self, standardMsg):
158 msg = self.test_case._formatMessage(self.msg, standardMsg)
159 raise self.test_case.failureException(msg)
160
Antoine Pitrou0715b9f2013-09-14 19:45:47 +0200161class _AssertRaisesBaseContext(_BaseTestCaseContext):
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000162
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300163 def __init__(self, expected, test_case, expected_regex=None):
Antoine Pitrou0715b9f2013-09-14 19:45:47 +0200164 _BaseTestCaseContext.__init__(self, test_case)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000165 self.expected = expected
Ezio Melottib4dc2502011-05-06 15:01:41 +0300166 self.test_case = test_case
R David Murrayef1c2672014-03-25 15:31:50 -0400167 if expected_regex is not None:
Ezio Melottied3a7d22010-12-01 02:32:32 +0000168 expected_regex = re.compile(expected_regex)
169 self.expected_regex = expected_regex
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300170 self.obj_name = None
Ezio Melottib4dc2502011-05-06 15:01:41 +0300171 self.msg = None
172
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300173 def handle(self, name, args, kwargs):
Ezio Melottib4dc2502011-05-06 15:01:41 +0300174 """
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300175 If args is empty, assertRaises/Warns is being used as a
Ezio Melottib4dc2502011-05-06 15:01:41 +0300176 context manager, so check for a 'msg' kwarg and return self.
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300177 If args is not empty, call a callable passing positional and keyword
178 arguments.
Ezio Melottib4dc2502011-05-06 15:01:41 +0300179 """
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300180 try:
Victor Stinnerbbd3cf82017-03-28 00:56:28 +0200181 if not _is_subtype(self.expected, self._base_type):
182 raise TypeError('%s() arg 1 must be %s' %
183 (name, self._base_type_str))
Victor Stinnerbbd3cf82017-03-28 00:56:28 +0200184 if not args:
185 self.msg = kwargs.pop('msg', None)
186 if kwargs:
Serhiy Storchaka77d57812018-08-19 10:00:11 +0300187 raise TypeError('%r is an invalid keyword argument for '
188 'this function' % (next(iter(kwargs)),))
Victor Stinnerbbd3cf82017-03-28 00:56:28 +0200189 return self
190
191 callable_obj, *args = args
192 try:
193 self.obj_name = callable_obj.__name__
194 except AttributeError:
195 self.obj_name = str(callable_obj)
196 with self:
197 callable_obj(*args, **kwargs)
198 finally:
199 # bpo-23890: manually break a reference cycle
200 self = None
Ezio Melottib4dc2502011-05-06 15:01:41 +0300201
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000202
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000203class _AssertRaisesContext(_AssertRaisesBaseContext):
204 """A context manager used to implement TestCase.assertRaises* methods."""
205
Serhiy Storchaka041dd8e2015-05-21 20:15:40 +0300206 _base_type = BaseException
207 _base_type_str = 'an exception type or tuple of exception types'
208
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000209 def __enter__(self):
Ezio Melotti49008232010-02-08 21:57:48 +0000210 return self
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000211
212 def __exit__(self, exc_type, exc_value, tb):
213 if exc_type is None:
214 try:
215 exc_name = self.expected.__name__
216 except AttributeError:
217 exc_name = str(self.expected)
218 if self.obj_name:
Ezio Melottib4dc2502011-05-06 15:01:41 +0300219 self._raiseFailure("{} not raised by {}".format(exc_name,
220 self.obj_name))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000221 else:
Ezio Melottib4dc2502011-05-06 15:01:41 +0300222 self._raiseFailure("{} not raised".format(exc_name))
Antoine Pitrou96810222014-04-29 01:23:50 +0200223 else:
224 traceback.clear_frames(tb)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000225 if not issubclass(exc_type, self.expected):
226 # let unexpected exceptions pass through
227 return False
Ezio Melotti49008232010-02-08 21:57:48 +0000228 # store exception, without traceback, for later retrieval
229 self.exception = exc_value.with_traceback(None)
Ezio Melottied3a7d22010-12-01 02:32:32 +0000230 if self.expected_regex is None:
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000231 return True
232
Ezio Melottied3a7d22010-12-01 02:32:32 +0000233 expected_regex = self.expected_regex
234 if not expected_regex.search(str(exc_value)):
Ezio Melottib4dc2502011-05-06 15:01:41 +0300235 self._raiseFailure('"{}" does not match "{}"'.format(
236 expected_regex.pattern, str(exc_value)))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000237 return True
238
239
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000240class _AssertWarnsContext(_AssertRaisesBaseContext):
241 """A context manager used to implement TestCase.assertWarns* methods."""
242
Serhiy Storchaka041dd8e2015-05-21 20:15:40 +0300243 _base_type = Warning
244 _base_type_str = 'a warning type or tuple of warning types'
245
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000246 def __enter__(self):
247 # The __warningregistry__'s need to be in a pristine state for tests
248 # to work properly.
249 for v in sys.modules.values():
250 if getattr(v, '__warningregistry__', None):
251 v.__warningregistry__ = {}
252 self.warnings_manager = warnings.catch_warnings(record=True)
253 self.warnings = self.warnings_manager.__enter__()
254 warnings.simplefilter("always", self.expected)
255 return self
256
257 def __exit__(self, exc_type, exc_value, tb):
258 self.warnings_manager.__exit__(exc_type, exc_value, tb)
259 if exc_type is not None:
260 # let unexpected exceptions pass through
261 return
262 try:
263 exc_name = self.expected.__name__
264 except AttributeError:
265 exc_name = str(self.expected)
266 first_matching = None
267 for m in self.warnings:
268 w = m.message
269 if not isinstance(w, self.expected):
270 continue
271 if first_matching is None:
272 first_matching = w
Ezio Melottied3a7d22010-12-01 02:32:32 +0000273 if (self.expected_regex is not None and
274 not self.expected_regex.search(str(w))):
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000275 continue
276 # store warning for later retrieval
277 self.warning = w
278 self.filename = m.filename
279 self.lineno = m.lineno
280 return
281 # Now we simply try to choose a helpful failure message
282 if first_matching is not None:
Ezio Melottib4dc2502011-05-06 15:01:41 +0300283 self._raiseFailure('"{}" does not match "{}"'.format(
284 self.expected_regex.pattern, str(first_matching)))
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000285 if self.obj_name:
Ezio Melottib4dc2502011-05-06 15:01:41 +0300286 self._raiseFailure("{} not triggered by {}".format(exc_name,
287 self.obj_name))
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000288 else:
Ezio Melottib4dc2502011-05-06 15:01:41 +0300289 self._raiseFailure("{} not triggered".format(exc_name))
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000290
291
Antoine Pitrou0715b9f2013-09-14 19:45:47 +0200292
293_LoggingWatcher = collections.namedtuple("_LoggingWatcher",
294 ["records", "output"])
295
296
297class _CapturingHandler(logging.Handler):
298 """
299 A logging handler capturing all (raw and formatted) logging output.
300 """
301
302 def __init__(self):
303 logging.Handler.__init__(self)
304 self.watcher = _LoggingWatcher([], [])
305
306 def flush(self):
307 pass
308
309 def emit(self, record):
310 self.watcher.records.append(record)
311 msg = self.format(record)
312 self.watcher.output.append(msg)
313
314
315
316class _AssertLogsContext(_BaseTestCaseContext):
317 """A context manager used to implement TestCase.assertLogs()."""
318
319 LOGGING_FORMAT = "%(levelname)s:%(name)s:%(message)s"
320
321 def __init__(self, test_case, logger_name, level):
322 _BaseTestCaseContext.__init__(self, test_case)
323 self.logger_name = logger_name
324 if level:
325 self.level = logging._nameToLevel.get(level, level)
326 else:
327 self.level = logging.INFO
328 self.msg = None
329
330 def __enter__(self):
331 if isinstance(self.logger_name, logging.Logger):
332 logger = self.logger = self.logger_name
333 else:
334 logger = self.logger = logging.getLogger(self.logger_name)
335 formatter = logging.Formatter(self.LOGGING_FORMAT)
336 handler = _CapturingHandler()
337 handler.setFormatter(formatter)
338 self.watcher = handler.watcher
339 self.old_handlers = logger.handlers[:]
340 self.old_level = logger.level
341 self.old_propagate = logger.propagate
342 logger.handlers = [handler]
343 logger.setLevel(self.level)
344 logger.propagate = False
345 return handler.watcher
346
347 def __exit__(self, exc_type, exc_value, tb):
348 self.logger.handlers = self.old_handlers
349 self.logger.propagate = self.old_propagate
350 self.logger.setLevel(self.old_level)
351 if exc_type is not None:
352 # let unexpected exceptions pass through
353 return False
354 if len(self.watcher.records) == 0:
355 self._raiseFailure(
356 "no logs of level {} or higher triggered on {}"
357 .format(logging.getLevelName(self.level), self.logger.name))
358
359
Serhiy Storchaka48fbe522017-06-23 21:47:39 +0300360class _OrderedChainMap(collections.ChainMap):
361 def __iter__(self):
362 seen = set()
363 for mapping in self.maps:
364 for k in mapping:
365 if k not in seen:
366 seen.add(k)
367 yield k
368
369
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000370class TestCase(object):
371 """A class whose instances are single test cases.
372
373 By default, the test code itself should be placed in a method named
374 'runTest'.
375
376 If the fixture may be used for many test cases, create as
377 many test methods as are needed. When instantiating such a TestCase
378 subclass, specify in the constructor arguments the name of the test method
379 that the instance is to execute.
380
381 Test authors should subclass TestCase for their own tests. Construction
382 and deconstruction of the test's environment ('fixture') can be
383 implemented by overriding the 'setUp' and 'tearDown' methods respectively.
384
385 If it is necessary to override the __init__ method, the base class
386 __init__ method must always be called. It is important that subclasses
387 should not change the signature of their __init__ method, since instances
388 of the classes are instantiated automatically by parts of the framework
389 in order to be run.
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000390
Ezio Melotti31797e52013-03-29 03:42:29 +0200391 When subclassing TestCase, you can set these attributes:
392 * failureException: determines which exception will be raised when
393 the instance's assertion methods fail; test methods raising this
394 exception will be deemed to have 'failed' rather than 'errored'.
395 * longMessage: determines whether long messages (including repr of
396 objects used in assert methods) will be printed on failure in *addition*
397 to any explicit message passed.
398 * maxDiff: sets the maximum length of a diff in failure messages
399 by assert methods using difflib. It is looked up as an instance
400 attribute so can be configured by individual tests if required.
401 """
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000402
403 failureException = AssertionError
404
Michael Foord5074df62010-12-03 00:53:09 +0000405 longMessage = True
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000406
Michael Foord085dfd32010-06-05 12:17:02 +0000407 maxDiff = 80*8
408
Ezio Melottiedd117f2011-04-27 10:20:38 +0300409 # If a string is longer than _diffThreshold, use normal comparison instead
410 # of difflib. See #11763.
411 _diffThreshold = 2**16
412
Benjamin Peterson847a4112010-03-14 15:04:17 +0000413 # Attribute used by TestSuite for classSetUp
414
415 _classSetupFailed = False
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000416
Lisa Roach0f221d02018-11-08 18:34:33 -0800417 _class_cleanups = []
418
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000419 def __init__(self, methodName='runTest'):
420 """Create an instance of the class that will use the named test
421 method when executed. Raises a ValueError if the instance does
422 not have a method with the specified name.
423 """
424 self._testMethodName = methodName
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100425 self._outcome = None
Michael Foord32e1d832011-01-03 17:00:11 +0000426 self._testMethodDoc = 'No test'
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000427 try:
428 testMethod = getattr(self, methodName)
429 except AttributeError:
Michael Foord32e1d832011-01-03 17:00:11 +0000430 if methodName != 'runTest':
431 # we allow instantiation with no explicit method name
432 # but not an *incorrect* or missing method name
433 raise ValueError("no such test method in %s: %s" %
434 (self.__class__, methodName))
435 else:
436 self._testMethodDoc = testMethod.__doc__
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000437 self._cleanups = []
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100438 self._subtest = None
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000439
440 # Map types to custom assertEqual functions that will compare
441 # instances of said type in more detail to generate a more useful
442 # error message.
Benjamin Peterson34b2b262011-07-12 19:21:42 -0500443 self._type_equality_funcs = {}
Michael Foord8ca6d982010-11-20 15:34:26 +0000444 self.addTypeEqualityFunc(dict, 'assertDictEqual')
445 self.addTypeEqualityFunc(list, 'assertListEqual')
446 self.addTypeEqualityFunc(tuple, 'assertTupleEqual')
447 self.addTypeEqualityFunc(set, 'assertSetEqual')
448 self.addTypeEqualityFunc(frozenset, 'assertSetEqual')
449 self.addTypeEqualityFunc(str, 'assertMultiLineEqual')
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000450
451 def addTypeEqualityFunc(self, typeobj, function):
452 """Add a type specific assertEqual style function to compare a type.
453
454 This method is for use by TestCase subclasses that need to register
455 their own type equality functions to provide nicer error messages.
456
457 Args:
458 typeobj: The data type to call this function on when both values
459 are of the same type in assertEqual().
460 function: The callable taking two arguments and an optional
461 msg= argument that raises self.failureException with a
462 useful error message when the two arguments are not equal.
463 """
Benjamin Peterson8f326b22009-12-13 02:10:36 +0000464 self._type_equality_funcs[typeobj] = function
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000465
Serhiy Storchaka142566c2019-06-05 18:22:31 +0300466 def addCleanup(self, function, /, *args, **kwargs):
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000467 """Add a function, with arguments, to be called when the test is
468 completed. Functions added are called on a LIFO basis and are
469 called after tearDown on test failure or success.
470
471 Cleanup items are called even if setUp fails (unlike tearDown)."""
472 self._cleanups.append((function, args, kwargs))
473
Serhiy Storchaka2085bd02019-06-01 11:00:15 +0300474 @classmethod
475 def addClassCleanup(cls, function, /, *args, **kwargs):
Lisa Roach0f221d02018-11-08 18:34:33 -0800476 """Same as addCleanup, except the cleanup items are called even if
477 setUpClass fails (unlike tearDownClass)."""
478 cls._class_cleanups.append((function, args, kwargs))
479
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000480 def setUp(self):
481 "Hook method for setting up the test fixture before exercising it."
482 pass
483
484 def tearDown(self):
485 "Hook method for deconstructing the test fixture after testing it."
486 pass
487
Benjamin Peterson847a4112010-03-14 15:04:17 +0000488 @classmethod
489 def setUpClass(cls):
490 "Hook method for setting up class fixture before running tests in the class."
491
492 @classmethod
493 def tearDownClass(cls):
494 "Hook method for deconstructing the class fixture after running all tests in the class."
495
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000496 def countTestCases(self):
497 return 1
498
499 def defaultTestResult(self):
500 return result.TestResult()
501
502 def shortDescription(self):
Michael Foord34c94622010-02-10 15:51:42 +0000503 """Returns a one-line description of the test, or None if no
504 description has been provided.
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000505
Michael Foord34c94622010-02-10 15:51:42 +0000506 The default implementation of this method returns the first line of
507 the specified test method's docstring.
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000508 """
Michael Foord34c94622010-02-10 15:51:42 +0000509 doc = self._testMethodDoc
510 return doc and doc.split("\n")[0].strip() or None
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000511
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000512
513 def id(self):
Benjamin Peterson847a4112010-03-14 15:04:17 +0000514 return "%s.%s" % (strclass(self.__class__), self._testMethodName)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000515
516 def __eq__(self, other):
517 if type(self) is not type(other):
518 return NotImplemented
519
520 return self._testMethodName == other._testMethodName
521
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000522 def __hash__(self):
523 return hash((type(self), self._testMethodName))
524
525 def __str__(self):
Benjamin Peterson847a4112010-03-14 15:04:17 +0000526 return "%s (%s)" % (self._testMethodName, strclass(self.__class__))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000527
528 def __repr__(self):
529 return "<%s testMethod=%s>" % \
Benjamin Peterson847a4112010-03-14 15:04:17 +0000530 (strclass(self.__class__), self._testMethodName)
531
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100532 def _addSkip(self, result, test_case, reason):
Benjamin Peterson847a4112010-03-14 15:04:17 +0000533 addSkip = getattr(result, 'addSkip', None)
534 if addSkip is not None:
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100535 addSkip(test_case, reason)
Benjamin Peterson847a4112010-03-14 15:04:17 +0000536 else:
537 warnings.warn("TestResult has no addSkip method, skips not reported",
538 RuntimeWarning, 2)
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100539 result.addSuccess(test_case)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000540
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100541 @contextlib.contextmanager
Berker Peksag16ea19f2016-09-21 19:34:15 +0300542 def subTest(self, msg=_subtest_msg_sentinel, **params):
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100543 """Return a context manager that will return the enclosed block
544 of code in a subtest identified by the optional message and
545 keyword parameters. A failure in the subtest marks the test
546 case as failed but resumes execution at the end of the enclosed
547 block, allowing further test code to be executed.
548 """
Bruno Oliveirada2bf9f2018-10-12 07:35:55 -0300549 if self._outcome is None or not self._outcome.result_supports_subtests:
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100550 yield
551 return
552 parent = self._subtest
553 if parent is None:
Serhiy Storchaka48fbe522017-06-23 21:47:39 +0300554 params_map = _OrderedChainMap(params)
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100555 else:
556 params_map = parent.params.new_child(params)
557 self._subtest = _SubTest(self, msg, params_map)
Michael Foordb3468f72010-12-19 03:19:47 +0000558 try:
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100559 with self._outcome.testPartExecutor(self._subtest, isTest=True):
560 yield
561 if not self._outcome.success:
562 result = self._outcome.result
563 if result is not None and result.failfast:
564 raise _ShouldStop
565 elif self._outcome.expectedFailure:
566 # If the test is expecting a failure, we really want to
567 # stop now and register the expected failure.
568 raise _ShouldStop
569 finally:
570 self._subtest = parent
571
572 def _feedErrorsToResult(self, result, errors):
573 for test, exc_info in errors:
574 if isinstance(test, _SubTest):
575 result.addSubTest(test.test_case, test, exc_info)
576 elif exc_info is not None:
577 if issubclass(exc_info[0], self.failureException):
578 result.addFailure(test, exc_info)
579 else:
580 result.addError(test, exc_info)
581
582 def _addExpectedFailure(self, result, exc_info):
583 try:
584 addExpectedFailure = result.addExpectedFailure
585 except AttributeError:
586 warnings.warn("TestResult has no addExpectedFailure method, reporting as passes",
587 RuntimeWarning)
588 result.addSuccess(self)
589 else:
590 addExpectedFailure(self, exc_info)
591
592 def _addUnexpectedSuccess(self, result):
593 try:
594 addUnexpectedSuccess = result.addUnexpectedSuccess
595 except AttributeError:
596 warnings.warn("TestResult has no addUnexpectedSuccess method, reporting as failure",
597 RuntimeWarning)
598 # We need to pass an actual exception and traceback to addFailure,
599 # otherwise the legacy result can choke.
600 try:
601 raise _UnexpectedSuccess from None
602 except _UnexpectedSuccess:
603 result.addFailure(self, sys.exc_info())
604 else:
605 addUnexpectedSuccess(self)
Michael Foordb3468f72010-12-19 03:19:47 +0000606
Andrew Svetlov4dd3e3f2019-05-29 12:33:59 +0300607 def _callSetUp(self):
608 self.setUp()
609
610 def _callTestMethod(self, method):
611 method()
612
613 def _callTearDown(self):
614 self.tearDown()
615
616 def _callCleanup(self, function, /, *args, **kwargs):
617 function(*args, **kwargs)
618
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000619 def run(self, result=None):
620 orig_result = result
621 if result is None:
622 result = self.defaultTestResult()
623 startTestRun = getattr(result, 'startTestRun', None)
624 if startTestRun is not None:
625 startTestRun()
626
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000627 result.startTest(self)
Benjamin Peterson847a4112010-03-14 15:04:17 +0000628
629 testMethod = getattr(self, self._testMethodName)
630 if (getattr(self.__class__, "__unittest_skip__", False) or
631 getattr(testMethod, "__unittest_skip__", False)):
632 # If the class or method was skipped.
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000633 try:
Benjamin Peterson847a4112010-03-14 15:04:17 +0000634 skip_why = (getattr(self.__class__, '__unittest_skip_why__', '')
635 or getattr(testMethod, '__unittest_skip_why__', ''))
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100636 self._addSkip(result, self, skip_why)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000637 finally:
638 result.stopTest(self)
639 return
Robert Collinsed599b72015-08-28 10:34:51 +1200640 expecting_failure_method = getattr(testMethod,
641 "__unittest_expecting_failure__", False)
642 expecting_failure_class = getattr(self,
643 "__unittest_expecting_failure__", False)
644 expecting_failure = expecting_failure_class or expecting_failure_method
Victor Stinner031bd532013-12-09 01:52:50 +0100645 outcome = _Outcome(result)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000646 try:
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100647 self._outcome = outcome
Michael Foordb3468f72010-12-19 03:19:47 +0000648
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100649 with outcome.testPartExecutor(self):
Andrew Svetlov4dd3e3f2019-05-29 12:33:59 +0300650 self._callSetUp()
Michael Foordb3468f72010-12-19 03:19:47 +0000651 if outcome.success:
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100652 outcome.expecting_failure = expecting_failure
653 with outcome.testPartExecutor(self, isTest=True):
Andrew Svetlov4dd3e3f2019-05-29 12:33:59 +0300654 self._callTestMethod(testMethod)
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100655 outcome.expecting_failure = False
656 with outcome.testPartExecutor(self):
Andrew Svetlov4dd3e3f2019-05-29 12:33:59 +0300657 self._callTearDown()
Michael Foordb3468f72010-12-19 03:19:47 +0000658
659 self.doCleanups()
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100660 for test, reason in outcome.skipped:
661 self._addSkip(result, test, reason)
662 self._feedErrorsToResult(result, outcome.errors)
Michael Foordb3468f72010-12-19 03:19:47 +0000663 if outcome.success:
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100664 if expecting_failure:
665 if outcome.expectedFailure:
666 self._addExpectedFailure(result, outcome.expectedFailure)
Benjamin Peterson847a4112010-03-14 15:04:17 +0000667 else:
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100668 self._addUnexpectedSuccess(result)
669 else:
670 result.addSuccess(self)
Michael Foord1341bb02011-03-14 19:01:46 -0400671 return result
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000672 finally:
673 result.stopTest(self)
674 if orig_result is None:
675 stopTestRun = getattr(result, 'stopTestRun', None)
676 if stopTestRun is not None:
677 stopTestRun()
678
Victor Stinner031bd532013-12-09 01:52:50 +0100679 # explicitly break reference cycles:
680 # outcome.errors -> frame -> outcome -> outcome.errors
681 # outcome.expectedFailure -> frame -> outcome -> outcome.expectedFailure
682 outcome.errors.clear()
683 outcome.expectedFailure = None
684
685 # clear the outcome, no more needed
686 self._outcome = None
687
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000688 def doCleanups(self):
689 """Execute all cleanup functions. Normally called for you after
690 tearDown."""
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100691 outcome = self._outcome or _Outcome()
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000692 while self._cleanups:
Michael Foordb3468f72010-12-19 03:19:47 +0000693 function, args, kwargs = self._cleanups.pop()
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100694 with outcome.testPartExecutor(self):
Andrew Svetlov4dd3e3f2019-05-29 12:33:59 +0300695 self._callCleanup(function, *args, **kwargs)
Michael Foordb3468f72010-12-19 03:19:47 +0000696
697 # return this for backwards compatibility
Lisa Roach0f221d02018-11-08 18:34:33 -0800698 # even though we no longer use it internally
Michael Foordb3468f72010-12-19 03:19:47 +0000699 return outcome.success
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000700
Lisa Roach0f221d02018-11-08 18:34:33 -0800701 @classmethod
702 def doClassCleanups(cls):
703 """Execute all class cleanup functions. Normally called for you after
704 tearDownClass."""
705 cls.tearDown_exceptions = []
706 while cls._class_cleanups:
707 function, args, kwargs = cls._class_cleanups.pop()
708 try:
709 function(*args, **kwargs)
710 except Exception as exc:
711 cls.tearDown_exceptions.append(sys.exc_info())
712
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000713 def __call__(self, *args, **kwds):
714 return self.run(*args, **kwds)
715
716 def debug(self):
717 """Run the test without collecting errors in a TestResult"""
718 self.setUp()
719 getattr(self, self._testMethodName)()
720 self.tearDown()
Michael Foordb8748742010-06-10 16:16:08 +0000721 while self._cleanups:
722 function, args, kwargs = self._cleanups.pop(-1)
723 function(*args, **kwargs)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000724
725 def skipTest(self, reason):
726 """Skip this test."""
727 raise SkipTest(reason)
728
729 def fail(self, msg=None):
730 """Fail immediately, with the given message."""
731 raise self.failureException(msg)
732
733 def assertFalse(self, expr, msg=None):
Ezio Melotti3044fa72010-12-18 17:31:58 +0000734 """Check that the expression is false."""
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000735 if expr:
Ezio Melotti3044fa72010-12-18 17:31:58 +0000736 msg = self._formatMessage(msg, "%s is not false" % safe_repr(expr))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000737 raise self.failureException(msg)
738
739 def assertTrue(self, expr, msg=None):
Ezio Melotti3044fa72010-12-18 17:31:58 +0000740 """Check that the expression is true."""
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000741 if not expr:
Ezio Melotti3044fa72010-12-18 17:31:58 +0000742 msg = self._formatMessage(msg, "%s is not true" % safe_repr(expr))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000743 raise self.failureException(msg)
744
745 def _formatMessage(self, msg, standardMsg):
746 """Honour the longMessage attribute when generating failure messages.
747 If longMessage is False this means:
748 * Use only an explicit message if it is provided
749 * Otherwise use the standard message for the assert
750
751 If longMessage is True:
752 * Use the standard message
753 * If an explicit message is provided, plus ' : ' and the explicit message
754 """
755 if not self.longMessage:
756 return msg or standardMsg
757 if msg is None:
758 return standardMsg
Benjamin Peterson847a4112010-03-14 15:04:17 +0000759 try:
760 # don't switch to '{}' formatting in Python 2.X
761 # it changes the way unicode input is handled
762 return '%s : %s' % (standardMsg, msg)
763 except UnicodeDecodeError:
764 return '%s : %s' % (safe_repr(standardMsg), safe_repr(msg))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000765
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300766 def assertRaises(self, expected_exception, *args, **kwargs):
767 """Fail unless an exception of class expected_exception is raised
768 by the callable when invoked with specified positional and
769 keyword arguments. If a different type of exception is
Andrew Svetlov737fb892012-12-18 21:14:22 +0200770 raised, it will not be caught, and the test case will be
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000771 deemed to have suffered an error, exactly as for an
772 unexpected exception.
773
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300774 If called with the callable and arguments omitted, will return a
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000775 context object used like this::
776
Michael Foord1c42b122010-02-05 22:58:21 +0000777 with self.assertRaises(SomeException):
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000778 do_something()
Michael Foord1c42b122010-02-05 22:58:21 +0000779
Ezio Melottib4dc2502011-05-06 15:01:41 +0300780 An optional keyword argument 'msg' can be provided when assertRaises
781 is used as a context object.
782
Michael Foord1c42b122010-02-05 22:58:21 +0000783 The context manager keeps a reference to the exception as
Ezio Melotti49008232010-02-08 21:57:48 +0000784 the 'exception' attribute. This allows you to inspect the
Michael Foord1c42b122010-02-05 22:58:21 +0000785 exception after the assertion::
786
787 with self.assertRaises(SomeException) as cm:
788 do_something()
Ezio Melotti49008232010-02-08 21:57:48 +0000789 the_exception = cm.exception
Michael Foordb57ac6d2010-02-05 23:26:29 +0000790 self.assertEqual(the_exception.error_code, 3)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000791 """
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300792 context = _AssertRaisesContext(expected_exception, self)
Victor Stinnerbbd3cf82017-03-28 00:56:28 +0200793 try:
794 return context.handle('assertRaises', args, kwargs)
795 finally:
796 # bpo-23890: manually break a reference cycle
797 context = None
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000798
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300799 def assertWarns(self, expected_warning, *args, **kwargs):
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000800 """Fail unless a warning of class warnClass is triggered
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300801 by the callable when invoked with specified positional and
802 keyword arguments. If a different type of warning is
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000803 triggered, it will not be handled: depending on the other
804 warning filtering rules in effect, it might be silenced, printed
805 out, or raised as an exception.
806
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300807 If called with the callable and arguments omitted, will return a
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000808 context object used like this::
809
810 with self.assertWarns(SomeWarning):
811 do_something()
812
Ezio Melottib4dc2502011-05-06 15:01:41 +0300813 An optional keyword argument 'msg' can be provided when assertWarns
814 is used as a context object.
815
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000816 The context manager keeps a reference to the first matching
817 warning as the 'warning' attribute; similarly, the 'filename'
818 and 'lineno' attributes give you information about the line
819 of Python code from which the warning was triggered.
820 This allows you to inspect the warning after the assertion::
821
822 with self.assertWarns(SomeWarning) as cm:
823 do_something()
824 the_warning = cm.warning
825 self.assertEqual(the_warning.some_attribute, 147)
826 """
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300827 context = _AssertWarnsContext(expected_warning, self)
828 return context.handle('assertWarns', args, kwargs)
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000829
Antoine Pitrou0715b9f2013-09-14 19:45:47 +0200830 def assertLogs(self, logger=None, level=None):
831 """Fail unless a log message of level *level* or higher is emitted
832 on *logger_name* or its children. If omitted, *level* defaults to
833 INFO and *logger* defaults to the root logger.
834
835 This method must be used as a context manager, and will yield
836 a recording object with two attributes: `output` and `records`.
837 At the end of the context manager, the `output` attribute will
838 be a list of the matching formatted log messages and the
839 `records` attribute will be a list of the corresponding LogRecord
840 objects.
841
842 Example::
843
844 with self.assertLogs('foo', level='INFO') as cm:
845 logging.getLogger('foo').info('first message')
846 logging.getLogger('foo.bar').error('second message')
847 self.assertEqual(cm.output, ['INFO:foo:first message',
848 'ERROR:foo.bar:second message'])
849 """
850 return _AssertLogsContext(self, logger, level)
851
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000852 def _getAssertEqualityFunc(self, first, second):
853 """Get a detailed comparison function for the types of the two args.
854
855 Returns: A callable accepting (first, second, msg=None) that will
856 raise a failure exception if first != second with a useful human
857 readable error message for those types.
858 """
859 #
860 # NOTE(gregory.p.smith): I considered isinstance(first, type(second))
861 # and vice versa. I opted for the conservative approach in case
862 # subclasses are not intended to be compared in detail to their super
863 # class instances using a type equality func. This means testing
864 # subtypes won't automagically use the detailed comparison. Callers
865 # should use their type specific assertSpamEqual method to compare
866 # subclasses if the detailed comparison is desired and appropriate.
867 # See the discussion in http://bugs.python.org/issue2578.
868 #
869 if type(first) is type(second):
870 asserter = self._type_equality_funcs.get(type(first))
871 if asserter is not None:
Benjamin Peterson34b2b262011-07-12 19:21:42 -0500872 if isinstance(asserter, str):
873 asserter = getattr(self, asserter)
Benjamin Peterson8f326b22009-12-13 02:10:36 +0000874 return asserter
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000875
876 return self._baseAssertEqual
877
878 def _baseAssertEqual(self, first, second, msg=None):
879 """The default assertEqual implementation, not type specific."""
880 if not first == second:
Serhiy Storchaka77622f52013-09-23 23:07:00 +0300881 standardMsg = '%s != %s' % _common_shorten_repr(first, second)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000882 msg = self._formatMessage(msg, standardMsg)
883 raise self.failureException(msg)
884
885 def assertEqual(self, first, second, msg=None):
886 """Fail if the two objects are unequal as determined by the '=='
887 operator.
888 """
889 assertion_func = self._getAssertEqualityFunc(first, second)
890 assertion_func(first, second, msg=msg)
891
892 def assertNotEqual(self, first, second, msg=None):
Ezio Melotti90eea972012-11-08 11:08:39 +0200893 """Fail if the two objects are equal as determined by the '!='
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000894 operator.
895 """
896 if not first != second:
Benjamin Peterson847a4112010-03-14 15:04:17 +0000897 msg = self._formatMessage(msg, '%s == %s' % (safe_repr(first),
898 safe_repr(second)))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000899 raise self.failureException(msg)
900
Michael Foord321d0592010-11-02 13:44:51 +0000901 def assertAlmostEqual(self, first, second, places=None, msg=None,
Benjamin Petersonb48af542010-04-11 20:43:16 +0000902 delta=None):
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000903 """Fail if the two objects are unequal as determined by their
904 difference rounded to the given number of decimal places
Benjamin Petersonb48af542010-04-11 20:43:16 +0000905 (default 7) and comparing to zero, or by comparing that the
Ron032a6482017-10-18 20:01:23 +0300906 difference between the two objects is more than the given
907 delta.
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000908
909 Note that decimal places (from zero) are usually not the same
Martin Pantereb995702016-07-28 01:11:04 +0000910 as significant digits (measured from the most significant digit).
Benjamin Peterson4ac9ce42009-10-04 14:49:41 +0000911
912 If the two objects compare equal then they will automatically
913 compare almost equal.
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000914 """
Benjamin Peterson4ac9ce42009-10-04 14:49:41 +0000915 if first == second:
Benjamin Petersonb48af542010-04-11 20:43:16 +0000916 # shortcut
Benjamin Peterson4ac9ce42009-10-04 14:49:41 +0000917 return
Benjamin Petersonb48af542010-04-11 20:43:16 +0000918 if delta is not None and places is not None:
919 raise TypeError("specify delta or places not both")
920
Giampaolo Rodola5d7a8d02017-05-01 18:18:56 +0200921 diff = abs(first - second)
Benjamin Petersonb48af542010-04-11 20:43:16 +0000922 if delta is not None:
Giampaolo Rodola5d7a8d02017-05-01 18:18:56 +0200923 if diff <= delta:
Benjamin Petersonb48af542010-04-11 20:43:16 +0000924 return
925
Giampaolo Rodola5d7a8d02017-05-01 18:18:56 +0200926 standardMsg = '%s != %s within %s delta (%s difference)' % (
927 safe_repr(first),
928 safe_repr(second),
929 safe_repr(delta),
930 safe_repr(diff))
Benjamin Petersonb48af542010-04-11 20:43:16 +0000931 else:
932 if places is None:
933 places = 7
934
Giampaolo Rodola5d7a8d02017-05-01 18:18:56 +0200935 if round(diff, places) == 0:
Benjamin Petersonb48af542010-04-11 20:43:16 +0000936 return
937
Giampaolo Rodola5d7a8d02017-05-01 18:18:56 +0200938 standardMsg = '%s != %s within %r places (%s difference)' % (
939 safe_repr(first),
940 safe_repr(second),
941 places,
942 safe_repr(diff))
Benjamin Petersonb48af542010-04-11 20:43:16 +0000943 msg = self._formatMessage(msg, standardMsg)
944 raise self.failureException(msg)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000945
Michael Foord321d0592010-11-02 13:44:51 +0000946 def assertNotAlmostEqual(self, first, second, places=None, msg=None,
Benjamin Petersonb48af542010-04-11 20:43:16 +0000947 delta=None):
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000948 """Fail if the two objects are equal as determined by their
949 difference rounded to the given number of decimal places
Benjamin Petersonb48af542010-04-11 20:43:16 +0000950 (default 7) and comparing to zero, or by comparing that the
Ron032a6482017-10-18 20:01:23 +0300951 difference between the two objects is less than the given delta.
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000952
953 Note that decimal places (from zero) are usually not the same
Martin Pantereb995702016-07-28 01:11:04 +0000954 as significant digits (measured from the most significant digit).
Benjamin Peterson4ac9ce42009-10-04 14:49:41 +0000955
956 Objects that are equal automatically fail.
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000957 """
Benjamin Petersonb48af542010-04-11 20:43:16 +0000958 if delta is not None and places is not None:
959 raise TypeError("specify delta or places not both")
Giampaolo Rodola5d7a8d02017-05-01 18:18:56 +0200960 diff = abs(first - second)
Benjamin Petersonb48af542010-04-11 20:43:16 +0000961 if delta is not None:
Giampaolo Rodola5d7a8d02017-05-01 18:18:56 +0200962 if not (first == second) and diff > delta:
Benjamin Petersonb48af542010-04-11 20:43:16 +0000963 return
Giampaolo Rodola5d7a8d02017-05-01 18:18:56 +0200964 standardMsg = '%s == %s within %s delta (%s difference)' % (
965 safe_repr(first),
966 safe_repr(second),
967 safe_repr(delta),
968 safe_repr(diff))
Benjamin Petersonb48af542010-04-11 20:43:16 +0000969 else:
970 if places is None:
971 places = 7
Giampaolo Rodola5d7a8d02017-05-01 18:18:56 +0200972 if not (first == second) and round(diff, places) != 0:
Benjamin Petersonb48af542010-04-11 20:43:16 +0000973 return
Benjamin Peterson847a4112010-03-14 15:04:17 +0000974 standardMsg = '%s == %s within %r places' % (safe_repr(first),
Benjamin Petersonb48af542010-04-11 20:43:16 +0000975 safe_repr(second),
976 places)
977
978 msg = self._formatMessage(msg, standardMsg)
979 raise self.failureException(msg)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000980
Michael Foord085dfd32010-06-05 12:17:02 +0000981 def assertSequenceEqual(self, seq1, seq2, msg=None, seq_type=None):
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000982 """An equality assertion for ordered sequences (like lists and tuples).
983
R. David Murrayad13f222010-01-29 22:17:58 +0000984 For the purposes of this function, a valid ordered sequence type is one
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000985 which can be indexed, has a length, and has an equality operator.
986
987 Args:
988 seq1: The first sequence to compare.
989 seq2: The second sequence to compare.
990 seq_type: The expected datatype of the sequences, or None if no
991 datatype should be enforced.
992 msg: Optional message to use on failure instead of a list of
993 differences.
994 """
Benjamin Petersonb29614e2012-10-09 11:16:03 -0400995 if seq_type is not None:
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000996 seq_type_name = seq_type.__name__
997 if not isinstance(seq1, seq_type):
Benjamin Peterson847a4112010-03-14 15:04:17 +0000998 raise self.failureException('First sequence is not a %s: %s'
999 % (seq_type_name, safe_repr(seq1)))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001000 if not isinstance(seq2, seq_type):
Benjamin Peterson847a4112010-03-14 15:04:17 +00001001 raise self.failureException('Second sequence is not a %s: %s'
1002 % (seq_type_name, safe_repr(seq2)))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001003 else:
1004 seq_type_name = "sequence"
1005
1006 differing = None
1007 try:
1008 len1 = len(seq1)
1009 except (TypeError, NotImplementedError):
1010 differing = 'First %s has no length. Non-sequence?' % (
1011 seq_type_name)
1012
1013 if differing is None:
1014 try:
1015 len2 = len(seq2)
1016 except (TypeError, NotImplementedError):
1017 differing = 'Second %s has no length. Non-sequence?' % (
1018 seq_type_name)
1019
1020 if differing is None:
1021 if seq1 == seq2:
1022 return
1023
Serhiy Storchaka77622f52013-09-23 23:07:00 +03001024 differing = '%ss differ: %s != %s\n' % (
1025 (seq_type_name.capitalize(),) +
1026 _common_shorten_repr(seq1, seq2))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001027
1028 for i in range(min(len1, len2)):
1029 try:
1030 item1 = seq1[i]
1031 except (TypeError, IndexError, NotImplementedError):
1032 differing += ('\nUnable to index element %d of first %s\n' %
1033 (i, seq_type_name))
1034 break
1035
1036 try:
1037 item2 = seq2[i]
1038 except (TypeError, IndexError, NotImplementedError):
1039 differing += ('\nUnable to index element %d of second %s\n' %
1040 (i, seq_type_name))
1041 break
1042
1043 if item1 != item2:
1044 differing += ('\nFirst differing element %d:\n%s\n%s\n' %
Serhiy Storchaka685fbed2016-04-25 08:58:25 +03001045 ((i,) + _common_shorten_repr(item1, item2)))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001046 break
1047 else:
1048 if (len1 == len2 and seq_type is None and
1049 type(seq1) != type(seq2)):
1050 # The sequences are the same, but have differing types.
1051 return
1052
1053 if len1 > len2:
1054 differing += ('\nFirst %s contains %d additional '
1055 'elements.\n' % (seq_type_name, len1 - len2))
1056 try:
1057 differing += ('First extra element %d:\n%s\n' %
Serhiy Storchaka685fbed2016-04-25 08:58:25 +03001058 (len2, safe_repr(seq1[len2])))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001059 except (TypeError, IndexError, NotImplementedError):
1060 differing += ('Unable to index element %d '
1061 'of first %s\n' % (len2, seq_type_name))
1062 elif len1 < len2:
1063 differing += ('\nSecond %s contains %d additional '
1064 'elements.\n' % (seq_type_name, len2 - len1))
1065 try:
1066 differing += ('First extra element %d:\n%s\n' %
Serhiy Storchaka685fbed2016-04-25 08:58:25 +03001067 (len1, safe_repr(seq2[len1])))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001068 except (TypeError, IndexError, NotImplementedError):
1069 differing += ('Unable to index element %d '
1070 'of second %s\n' % (len1, seq_type_name))
Michael Foord2034d9a2010-06-05 11:27:52 +00001071 standardMsg = differing
1072 diffMsg = '\n' + '\n'.join(
Benjamin Peterson6e8c7572009-10-04 20:19:21 +00001073 difflib.ndiff(pprint.pformat(seq1).splitlines(),
1074 pprint.pformat(seq2).splitlines()))
Michael Foord085dfd32010-06-05 12:17:02 +00001075
1076 standardMsg = self._truncateMessage(standardMsg, diffMsg)
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001077 msg = self._formatMessage(msg, standardMsg)
1078 self.fail(msg)
1079
Michael Foord085dfd32010-06-05 12:17:02 +00001080 def _truncateMessage(self, message, diff):
1081 max_diff = self.maxDiff
1082 if max_diff is None or len(diff) <= max_diff:
1083 return message + diff
Michael Foord9dad32e2010-06-05 13:49:56 +00001084 return message + (DIFF_OMITTED % len(diff))
Michael Foord085dfd32010-06-05 12:17:02 +00001085
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001086 def assertListEqual(self, list1, list2, msg=None):
1087 """A list-specific equality assertion.
1088
1089 Args:
1090 list1: The first list to compare.
1091 list2: The second list to compare.
1092 msg: Optional message to use on failure instead of a list of
1093 differences.
1094
1095 """
1096 self.assertSequenceEqual(list1, list2, msg, seq_type=list)
1097
1098 def assertTupleEqual(self, tuple1, tuple2, msg=None):
1099 """A tuple-specific equality assertion.
1100
1101 Args:
1102 tuple1: The first tuple to compare.
1103 tuple2: The second tuple to compare.
1104 msg: Optional message to use on failure instead of a list of
1105 differences.
1106 """
1107 self.assertSequenceEqual(tuple1, tuple2, msg, seq_type=tuple)
1108
1109 def assertSetEqual(self, set1, set2, msg=None):
1110 """A set-specific equality assertion.
1111
1112 Args:
1113 set1: The first set to compare.
1114 set2: The second set to compare.
1115 msg: Optional message to use on failure instead of a list of
1116 differences.
1117
Michael Foord91c9da32010-03-20 17:21:27 +00001118 assertSetEqual uses ducktyping to support different types of sets, and
1119 is optimized for sets specifically (parameters must support a
1120 difference method).
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001121 """
1122 try:
1123 difference1 = set1.difference(set2)
1124 except TypeError as e:
1125 self.fail('invalid type when attempting set difference: %s' % e)
1126 except AttributeError as e:
1127 self.fail('first argument does not support set difference: %s' % e)
1128
1129 try:
1130 difference2 = set2.difference(set1)
1131 except TypeError as e:
1132 self.fail('invalid type when attempting set difference: %s' % e)
1133 except AttributeError as e:
1134 self.fail('second argument does not support set difference: %s' % e)
1135
1136 if not (difference1 or difference2):
1137 return
1138
1139 lines = []
1140 if difference1:
1141 lines.append('Items in the first set but not the second:')
1142 for item in difference1:
1143 lines.append(repr(item))
1144 if difference2:
1145 lines.append('Items in the second set but not the first:')
1146 for item in difference2:
1147 lines.append(repr(item))
1148
1149 standardMsg = '\n'.join(lines)
1150 self.fail(self._formatMessage(msg, standardMsg))
1151
1152 def assertIn(self, member, container, msg=None):
1153 """Just like self.assertTrue(a in b), but with a nicer default message."""
1154 if member not in container:
Benjamin Peterson847a4112010-03-14 15:04:17 +00001155 standardMsg = '%s not found in %s' % (safe_repr(member),
1156 safe_repr(container))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001157 self.fail(self._formatMessage(msg, standardMsg))
1158
1159 def assertNotIn(self, member, container, msg=None):
1160 """Just like self.assertTrue(a not in b), but with a nicer default message."""
1161 if member in container:
Benjamin Peterson847a4112010-03-14 15:04:17 +00001162 standardMsg = '%s unexpectedly found in %s' % (safe_repr(member),
1163 safe_repr(container))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001164 self.fail(self._formatMessage(msg, standardMsg))
1165
1166 def assertIs(self, expr1, expr2, msg=None):
1167 """Just like self.assertTrue(a is b), but with a nicer default message."""
1168 if expr1 is not expr2:
Benjamin Peterson847a4112010-03-14 15:04:17 +00001169 standardMsg = '%s is not %s' % (safe_repr(expr1),
1170 safe_repr(expr2))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001171 self.fail(self._formatMessage(msg, standardMsg))
1172
1173 def assertIsNot(self, expr1, expr2, msg=None):
1174 """Just like self.assertTrue(a is not b), but with a nicer default message."""
1175 if expr1 is expr2:
Benjamin Peterson847a4112010-03-14 15:04:17 +00001176 standardMsg = 'unexpectedly identical: %s' % (safe_repr(expr1),)
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001177 self.fail(self._formatMessage(msg, standardMsg))
1178
1179 def assertDictEqual(self, d1, d2, msg=None):
Ezio Melottib3aedd42010-11-20 19:04:17 +00001180 self.assertIsInstance(d1, dict, 'First argument is not a dictionary')
1181 self.assertIsInstance(d2, dict, 'Second argument is not a dictionary')
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001182
1183 if d1 != d2:
Serhiy Storchaka77622f52013-09-23 23:07:00 +03001184 standardMsg = '%s != %s' % _common_shorten_repr(d1, d2)
Michael Foord085dfd32010-06-05 12:17:02 +00001185 diff = ('\n' + '\n'.join(difflib.ndiff(
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001186 pprint.pformat(d1).splitlines(),
1187 pprint.pformat(d2).splitlines())))
Michael Foordcb11b252010-06-05 13:14:43 +00001188 standardMsg = self._truncateMessage(standardMsg, diff)
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001189 self.fail(self._formatMessage(msg, standardMsg))
1190
Ezio Melotti0f535012011-04-03 18:02:13 +03001191 def assertDictContainsSubset(self, subset, dictionary, msg=None):
1192 """Checks whether dictionary is a superset of subset."""
1193 warnings.warn('assertDictContainsSubset is deprecated',
1194 DeprecationWarning)
1195 missing = []
1196 mismatched = []
1197 for key, value in subset.items():
1198 if key not in dictionary:
1199 missing.append(key)
1200 elif value != dictionary[key]:
1201 mismatched.append('%s, expected: %s, actual: %s' %
1202 (safe_repr(key), safe_repr(value),
1203 safe_repr(dictionary[key])))
1204
1205 if not (missing or mismatched):
1206 return
1207
1208 standardMsg = ''
1209 if missing:
1210 standardMsg = 'Missing: %s' % ','.join(safe_repr(m) for m in
1211 missing)
1212 if mismatched:
1213 if standardMsg:
1214 standardMsg += '; '
1215 standardMsg += 'Mismatched values: %s' % ','.join(mismatched)
1216
1217 self.fail(self._formatMessage(msg, standardMsg))
1218
1219
Raymond Hettinger57bd00a2010-12-24 21:51:48 +00001220 def assertCountEqual(self, first, second, msg=None):
jkleint39baace2019-04-23 01:34:29 -07001221 """Asserts that two iterables have the same elements, the same number of
1222 times, without regard to order.
Michael Foord8442a602010-03-20 16:58:04 +00001223
Raymond Hettinger57bd00a2010-12-24 21:51:48 +00001224 self.assertEqual(Counter(list(first)),
1225 Counter(list(second)))
Michael Foord8442a602010-03-20 16:58:04 +00001226
Raymond Hettinger57bd00a2010-12-24 21:51:48 +00001227 Example:
Michael Foord8442a602010-03-20 16:58:04 +00001228 - [0, 1, 1] and [1, 0, 1] compare equal.
1229 - [0, 0, 1] and [0, 1] compare unequal.
Raymond Hettinger57bd00a2010-12-24 21:51:48 +00001230
Michael Foord8442a602010-03-20 16:58:04 +00001231 """
Michael Foorde180d392011-01-28 19:51:48 +00001232 first_seq, second_seq = list(first), list(second)
Michael Foord8442a602010-03-20 16:58:04 +00001233 try:
Michael Foorde180d392011-01-28 19:51:48 +00001234 first = collections.Counter(first_seq)
1235 second = collections.Counter(second_seq)
Michael Foord8442a602010-03-20 16:58:04 +00001236 except TypeError:
Raymond Hettinger6518f5e2010-12-24 00:52:54 +00001237 # Handle case with unhashable elements
Michael Foorde180d392011-01-28 19:51:48 +00001238 differences = _count_diff_all_purpose(first_seq, second_seq)
Michael Foord8442a602010-03-20 16:58:04 +00001239 else:
Michael Foorde180d392011-01-28 19:51:48 +00001240 if first == second:
Raymond Hettinger6e165b32010-11-27 09:31:37 +00001241 return
Michael Foorde180d392011-01-28 19:51:48 +00001242 differences = _count_diff_hashable(first_seq, second_seq)
Michael Foord8442a602010-03-20 16:58:04 +00001243
Raymond Hettinger93e233d2010-12-24 10:02:22 +00001244 if differences:
1245 standardMsg = 'Element counts were not equal:\n'
Raymond Hettinger57bd00a2010-12-24 21:51:48 +00001246 lines = ['First has %d, Second has %d: %r' % diff for diff in differences]
Raymond Hettinger93e233d2010-12-24 10:02:22 +00001247 diffMsg = '\n'.join(lines)
1248 standardMsg = self._truncateMessage(standardMsg, diffMsg)
1249 msg = self._formatMessage(msg, standardMsg)
1250 self.fail(msg)
Michael Foord8442a602010-03-20 16:58:04 +00001251
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001252 def assertMultiLineEqual(self, first, second, msg=None):
1253 """Assert that two multi-line strings are equal."""
Ezio Melottib3aedd42010-11-20 19:04:17 +00001254 self.assertIsInstance(first, str, 'First argument is not a string')
1255 self.assertIsInstance(second, str, 'Second argument is not a string')
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001256
1257 if first != second:
Ezio Melottiedd117f2011-04-27 10:20:38 +03001258 # don't use difflib if the strings are too long
1259 if (len(first) > self._diffThreshold or
1260 len(second) > self._diffThreshold):
1261 self._baseAssertEqual(first, second, msg)
Ezio Melottid8b509b2011-09-28 17:37:55 +03001262 firstlines = first.splitlines(keepends=True)
1263 secondlines = second.splitlines(keepends=True)
Michael Foordc653ce32010-07-10 13:52:22 +00001264 if len(firstlines) == 1 and first.strip('\r\n') == first:
1265 firstlines = [first + '\n']
1266 secondlines = [second + '\n']
Serhiy Storchaka77622f52013-09-23 23:07:00 +03001267 standardMsg = '%s != %s' % _common_shorten_repr(first, second)
Michael Foordc653ce32010-07-10 13:52:22 +00001268 diff = '\n' + ''.join(difflib.ndiff(firstlines, secondlines))
Michael Foordcb11b252010-06-05 13:14:43 +00001269 standardMsg = self._truncateMessage(standardMsg, diff)
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001270 self.fail(self._formatMessage(msg, standardMsg))
1271
1272 def assertLess(self, a, b, msg=None):
1273 """Just like self.assertTrue(a < b), but with a nicer default message."""
1274 if not a < b:
Benjamin Peterson847a4112010-03-14 15:04:17 +00001275 standardMsg = '%s not less than %s' % (safe_repr(a), safe_repr(b))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001276 self.fail(self._formatMessage(msg, standardMsg))
1277
1278 def assertLessEqual(self, a, b, msg=None):
1279 """Just like self.assertTrue(a <= b), but with a nicer default message."""
1280 if not a <= b:
Benjamin Peterson847a4112010-03-14 15:04:17 +00001281 standardMsg = '%s not less than or equal to %s' % (safe_repr(a), safe_repr(b))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001282 self.fail(self._formatMessage(msg, standardMsg))
1283
1284 def assertGreater(self, a, b, msg=None):
1285 """Just like self.assertTrue(a > b), but with a nicer default message."""
1286 if not a > b:
Benjamin Peterson847a4112010-03-14 15:04:17 +00001287 standardMsg = '%s not greater than %s' % (safe_repr(a), safe_repr(b))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001288 self.fail(self._formatMessage(msg, standardMsg))
1289
1290 def assertGreaterEqual(self, a, b, msg=None):
1291 """Just like self.assertTrue(a >= b), but with a nicer default message."""
1292 if not a >= b:
Benjamin Peterson847a4112010-03-14 15:04:17 +00001293 standardMsg = '%s not greater than or equal to %s' % (safe_repr(a), safe_repr(b))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001294 self.fail(self._formatMessage(msg, standardMsg))
1295
1296 def assertIsNone(self, obj, msg=None):
1297 """Same as self.assertTrue(obj is None), with a nicer default message."""
1298 if obj is not None:
Benjamin Peterson847a4112010-03-14 15:04:17 +00001299 standardMsg = '%s is not None' % (safe_repr(obj),)
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001300 self.fail(self._formatMessage(msg, standardMsg))
1301
1302 def assertIsNotNone(self, obj, msg=None):
1303 """Included for symmetry with assertIsNone."""
1304 if obj is None:
1305 standardMsg = 'unexpectedly None'
1306 self.fail(self._formatMessage(msg, standardMsg))
1307
Benjamin Peterson6e8c7572009-10-04 20:19:21 +00001308 def assertIsInstance(self, obj, cls, msg=None):
1309 """Same as self.assertTrue(isinstance(obj, cls)), with a nicer
1310 default message."""
1311 if not isinstance(obj, cls):
Benjamin Peterson847a4112010-03-14 15:04:17 +00001312 standardMsg = '%s is not an instance of %r' % (safe_repr(obj), cls)
Benjamin Peterson6e8c7572009-10-04 20:19:21 +00001313 self.fail(self._formatMessage(msg, standardMsg))
1314
1315 def assertNotIsInstance(self, obj, cls, msg=None):
1316 """Included for symmetry with assertIsInstance."""
1317 if isinstance(obj, cls):
Benjamin Peterson847a4112010-03-14 15:04:17 +00001318 standardMsg = '%s is an instance of %r' % (safe_repr(obj), cls)
Benjamin Peterson6e8c7572009-10-04 20:19:21 +00001319 self.fail(self._formatMessage(msg, standardMsg))
1320
Ezio Melottied3a7d22010-12-01 02:32:32 +00001321 def assertRaisesRegex(self, expected_exception, expected_regex,
Serhiy Storchakadf573d62015-05-16 16:29:50 +03001322 *args, **kwargs):
Ezio Melottied3a7d22010-12-01 02:32:32 +00001323 """Asserts that the message in a raised exception matches a regex.
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001324
1325 Args:
1326 expected_exception: Exception class expected to be raised.
Serhiy Storchaka0b5e61d2017-10-04 20:09:49 +03001327 expected_regex: Regex (re.Pattern object or string) expected
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001328 to be found in error message.
Serhiy Storchakadf573d62015-05-16 16:29:50 +03001329 args: Function to be called and extra positional args.
1330 kwargs: Extra kwargs.
Ezio Melottib4dc2502011-05-06 15:01:41 +03001331 msg: Optional message used in case of failure. Can only be used
1332 when assertRaisesRegex is used as a context manager.
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001333 """
Serhiy Storchakadf573d62015-05-16 16:29:50 +03001334 context = _AssertRaisesContext(expected_exception, self, expected_regex)
1335 return context.handle('assertRaisesRegex', args, kwargs)
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001336
Ezio Melottied3a7d22010-12-01 02:32:32 +00001337 def assertWarnsRegex(self, expected_warning, expected_regex,
Serhiy Storchakadf573d62015-05-16 16:29:50 +03001338 *args, **kwargs):
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +00001339 """Asserts that the message in a triggered warning matches a regexp.
1340 Basic functioning is similar to assertWarns() with the addition
1341 that only warnings whose messages also match the regular expression
1342 are considered successful matches.
1343
1344 Args:
1345 expected_warning: Warning class expected to be triggered.
Serhiy Storchaka0b5e61d2017-10-04 20:09:49 +03001346 expected_regex: Regex (re.Pattern object or string) expected
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +00001347 to be found in error message.
Serhiy Storchakadf573d62015-05-16 16:29:50 +03001348 args: Function to be called and extra positional args.
1349 kwargs: Extra kwargs.
Ezio Melottib4dc2502011-05-06 15:01:41 +03001350 msg: Optional message used in case of failure. Can only be used
1351 when assertWarnsRegex is used as a context manager.
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +00001352 """
Serhiy Storchakadf573d62015-05-16 16:29:50 +03001353 context = _AssertWarnsContext(expected_warning, self, expected_regex)
1354 return context.handle('assertWarnsRegex', args, kwargs)
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +00001355
Ezio Melottied3a7d22010-12-01 02:32:32 +00001356 def assertRegex(self, text, expected_regex, msg=None):
Michael Foorde3ef5f12010-05-08 16:46:14 +00001357 """Fail the test unless the text matches the regular expression."""
Ezio Melottied3a7d22010-12-01 02:32:32 +00001358 if isinstance(expected_regex, (str, bytes)):
Gregory P. Smithed16bf42010-12-16 19:23:05 +00001359 assert expected_regex, "expected_regex must not be empty."
Ezio Melottied3a7d22010-12-01 02:32:32 +00001360 expected_regex = re.compile(expected_regex)
1361 if not expected_regex.search(text):
Robert Collinsbe6caca2015-08-20 11:13:09 +12001362 standardMsg = "Regex didn't match: %r not found in %r" % (
1363 expected_regex.pattern, text)
1364 # _formatMessage ensures the longMessage option is respected
1365 msg = self._formatMessage(msg, standardMsg)
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001366 raise self.failureException(msg)
1367
Ezio Melotti8f776302010-12-10 02:32:05 +00001368 def assertNotRegex(self, text, unexpected_regex, msg=None):
Michael Foorde3ef5f12010-05-08 16:46:14 +00001369 """Fail the test if the text matches the regular expression."""
Ezio Melottied3a7d22010-12-01 02:32:32 +00001370 if isinstance(unexpected_regex, (str, bytes)):
1371 unexpected_regex = re.compile(unexpected_regex)
1372 match = unexpected_regex.search(text)
Benjamin Petersonb48af542010-04-11 20:43:16 +00001373 if match:
Robert Collinsbe6caca2015-08-20 11:13:09 +12001374 standardMsg = 'Regex matched: %r matches %r in %r' % (
1375 text[match.start() : match.end()],
1376 unexpected_regex.pattern,
1377 text)
1378 # _formatMessage ensures the longMessage option is respected
1379 msg = self._formatMessage(msg, standardMsg)
Benjamin Petersonb48af542010-04-11 20:43:16 +00001380 raise self.failureException(msg)
1381
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001382
Ezio Melottied3a7d22010-12-01 02:32:32 +00001383 def _deprecate(original_func):
1384 def deprecated_func(*args, **kwargs):
1385 warnings.warn(
1386 'Please use {0} instead.'.format(original_func.__name__),
1387 DeprecationWarning, 2)
1388 return original_func(*args, **kwargs)
1389 return deprecated_func
1390
Ezio Melotti361467e2011-04-03 17:37:58 +03001391 # see #9424
Ezio Melotti0f535012011-04-03 18:02:13 +03001392 failUnlessEqual = assertEquals = _deprecate(assertEqual)
1393 failIfEqual = assertNotEquals = _deprecate(assertNotEqual)
1394 failUnlessAlmostEqual = assertAlmostEquals = _deprecate(assertAlmostEqual)
1395 failIfAlmostEqual = assertNotAlmostEquals = _deprecate(assertNotAlmostEqual)
1396 failUnless = assert_ = _deprecate(assertTrue)
1397 failUnlessRaises = _deprecate(assertRaises)
1398 failIf = _deprecate(assertFalse)
Ezio Melottied3a7d22010-12-01 02:32:32 +00001399 assertRaisesRegexp = _deprecate(assertRaisesRegex)
1400 assertRegexpMatches = _deprecate(assertRegex)
Robert Collinsbe6caca2015-08-20 11:13:09 +12001401 assertNotRegexpMatches = _deprecate(assertNotRegex)
Ezio Melottied3a7d22010-12-01 02:32:32 +00001402
1403
1404
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001405class FunctionTestCase(TestCase):
1406 """A test case that wraps a test function.
1407
1408 This is useful for slipping pre-existing test functions into the
1409 unittest framework. Optionally, set-up and tidy-up functions can be
1410 supplied. As with TestCase, the tidy-up ('tearDown') function will
1411 always be called if the set-up ('setUp') function ran successfully.
1412 """
1413
1414 def __init__(self, testFunc, setUp=None, tearDown=None, description=None):
1415 super(FunctionTestCase, self).__init__()
1416 self._setUpFunc = setUp
1417 self._tearDownFunc = tearDown
1418 self._testFunc = testFunc
1419 self._description = description
1420
1421 def setUp(self):
1422 if self._setUpFunc is not None:
1423 self._setUpFunc()
1424
1425 def tearDown(self):
1426 if self._tearDownFunc is not None:
1427 self._tearDownFunc()
1428
1429 def runTest(self):
1430 self._testFunc()
1431
1432 def id(self):
1433 return self._testFunc.__name__
1434
1435 def __eq__(self, other):
1436 if not isinstance(other, self.__class__):
1437 return NotImplemented
1438
1439 return self._setUpFunc == other._setUpFunc and \
1440 self._tearDownFunc == other._tearDownFunc and \
1441 self._testFunc == other._testFunc and \
1442 self._description == other._description
1443
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001444 def __hash__(self):
1445 return hash((type(self), self._setUpFunc, self._tearDownFunc,
1446 self._testFunc, self._description))
1447
1448 def __str__(self):
Benjamin Peterson847a4112010-03-14 15:04:17 +00001449 return "%s (%s)" % (strclass(self.__class__),
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001450 self._testFunc.__name__)
1451
1452 def __repr__(self):
Benjamin Peterson847a4112010-03-14 15:04:17 +00001453 return "<%s tec=%s>" % (strclass(self.__class__),
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001454 self._testFunc)
1455
1456 def shortDescription(self):
1457 if self._description is not None:
1458 return self._description
1459 doc = self._testFunc.__doc__
1460 return doc and doc.split("\n")[0].strip() or None
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +01001461
1462
1463class _SubTest(TestCase):
1464
1465 def __init__(self, test_case, message, params):
1466 super().__init__()
1467 self._message = message
1468 self.test_case = test_case
1469 self.params = params
1470 self.failureException = test_case.failureException
1471
1472 def runTest(self):
1473 raise NotImplementedError("subtests cannot be run directly")
1474
1475 def _subDescription(self):
1476 parts = []
Berker Peksag16ea19f2016-09-21 19:34:15 +03001477 if self._message is not _subtest_msg_sentinel:
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +01001478 parts.append("[{}]".format(self._message))
1479 if self.params:
1480 params_desc = ', '.join(
1481 "{}={!r}".format(k, v)
Serhiy Storchaka48fbe522017-06-23 21:47:39 +03001482 for (k, v) in self.params.items())
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +01001483 parts.append("({})".format(params_desc))
1484 return " ".join(parts) or '(<subtest>)'
1485
1486 def id(self):
1487 return "{} {}".format(self.test_case.id(), self._subDescription())
1488
1489 def shortDescription(self):
1490 """Returns a one-line description of the subtest, or None if no
1491 description has been provided.
1492 """
1493 return self.test_case.shortDescription()
1494
1495 def __str__(self):
1496 return "{} {}".format(self.test_case, self._subDescription())