blob: 7b1e86941315e85aa923c39b4fe15f2702264ce9 [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 Storchaka42a139e2019-04-01 09:16:35 +030089def addModuleCleanup(*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)."""
Serhiy Storchaka42a139e2019-04-01 09:16:35 +030092 if args:
93 function, *args = args
94 elif 'function' in kwargs:
95 function = kwargs.pop('function')
96 import warnings
97 warnings.warn("Passing 'function' as keyword argument is deprecated",
98 DeprecationWarning, stacklevel=2)
99 else:
100 raise TypeError('addModuleCleanup expected at least 1 positional '
101 'argument, got %d' % (len(args)-1))
102 args = tuple(args)
103
Lisa Roach0f221d02018-11-08 18:34:33 -0800104 _module_cleanups.append((function, args, kwargs))
Serhiy Storchakad53cf992019-05-06 22:40:27 +0300105addModuleCleanup.__text_signature__ = '(function, /, *args, **kwargs)'
Lisa Roach0f221d02018-11-08 18:34:33 -0800106
107
108def doModuleCleanups():
109 """Execute all module cleanup functions. Normally called for you after
110 tearDownModule."""
111 exceptions = []
112 while _module_cleanups:
113 function, args, kwargs = _module_cleanups.pop()
114 try:
115 function(*args, **kwargs)
116 except Exception as exc:
117 exceptions.append(exc)
118 if exceptions:
119 # Swallows all but first exception. If a multi-exception handler
120 # gets written we should use that here instead.
121 raise exceptions[0]
122
123
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000124def skip(reason):
125 """
126 Unconditionally skip a test.
127 """
128 def decorator(test_item):
Antoine Pitroub05ac862012-04-25 14:56:46 +0200129 if not isinstance(test_item, type):
Benjamin Peterson847a4112010-03-14 15:04:17 +0000130 @functools.wraps(test_item)
131 def skip_wrapper(*args, **kwargs):
132 raise SkipTest(reason)
133 test_item = skip_wrapper
134
135 test_item.__unittest_skip__ = True
136 test_item.__unittest_skip_why__ = reason
137 return test_item
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000138 return decorator
139
140def skipIf(condition, reason):
141 """
142 Skip a test if the condition is true.
143 """
144 if condition:
145 return skip(reason)
146 return _id
147
148def skipUnless(condition, reason):
149 """
150 Skip a test unless the condition is true.
151 """
152 if not condition:
153 return skip(reason)
154 return _id
155
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100156def expectedFailure(test_item):
157 test_item.__unittest_expecting_failure__ = True
158 return test_item
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000159
Serhiy Storchaka041dd8e2015-05-21 20:15:40 +0300160def _is_subtype(expected, basetype):
161 if isinstance(expected, tuple):
162 return all(_is_subtype(e, basetype) for e in expected)
163 return isinstance(expected, type) and issubclass(expected, basetype)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000164
Antoine Pitrou0715b9f2013-09-14 19:45:47 +0200165class _BaseTestCaseContext:
166
167 def __init__(self, test_case):
168 self.test_case = test_case
169
170 def _raiseFailure(self, standardMsg):
171 msg = self.test_case._formatMessage(self.msg, standardMsg)
172 raise self.test_case.failureException(msg)
173
Antoine Pitrou0715b9f2013-09-14 19:45:47 +0200174class _AssertRaisesBaseContext(_BaseTestCaseContext):
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000175
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300176 def __init__(self, expected, test_case, expected_regex=None):
Antoine Pitrou0715b9f2013-09-14 19:45:47 +0200177 _BaseTestCaseContext.__init__(self, test_case)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000178 self.expected = expected
Ezio Melottib4dc2502011-05-06 15:01:41 +0300179 self.test_case = test_case
R David Murrayef1c2672014-03-25 15:31:50 -0400180 if expected_regex is not None:
Ezio Melottied3a7d22010-12-01 02:32:32 +0000181 expected_regex = re.compile(expected_regex)
182 self.expected_regex = expected_regex
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300183 self.obj_name = None
Ezio Melottib4dc2502011-05-06 15:01:41 +0300184 self.msg = None
185
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300186 def handle(self, name, args, kwargs):
Ezio Melottib4dc2502011-05-06 15:01:41 +0300187 """
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300188 If args is empty, assertRaises/Warns is being used as a
Ezio Melottib4dc2502011-05-06 15:01:41 +0300189 context manager, so check for a 'msg' kwarg and return self.
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300190 If args is not empty, call a callable passing positional and keyword
191 arguments.
Ezio Melottib4dc2502011-05-06 15:01:41 +0300192 """
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300193 try:
Victor Stinnerbbd3cf82017-03-28 00:56:28 +0200194 if not _is_subtype(self.expected, self._base_type):
195 raise TypeError('%s() arg 1 must be %s' %
196 (name, self._base_type_str))
Victor Stinnerbbd3cf82017-03-28 00:56:28 +0200197 if not args:
198 self.msg = kwargs.pop('msg', None)
199 if kwargs:
Serhiy Storchaka77d57812018-08-19 10:00:11 +0300200 raise TypeError('%r is an invalid keyword argument for '
201 'this function' % (next(iter(kwargs)),))
Victor Stinnerbbd3cf82017-03-28 00:56:28 +0200202 return self
203
204 callable_obj, *args = args
205 try:
206 self.obj_name = callable_obj.__name__
207 except AttributeError:
208 self.obj_name = str(callable_obj)
209 with self:
210 callable_obj(*args, **kwargs)
211 finally:
212 # bpo-23890: manually break a reference cycle
213 self = None
Ezio Melottib4dc2502011-05-06 15:01:41 +0300214
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000215
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000216class _AssertRaisesContext(_AssertRaisesBaseContext):
217 """A context manager used to implement TestCase.assertRaises* methods."""
218
Serhiy Storchaka041dd8e2015-05-21 20:15:40 +0300219 _base_type = BaseException
220 _base_type_str = 'an exception type or tuple of exception types'
221
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000222 def __enter__(self):
Ezio Melotti49008232010-02-08 21:57:48 +0000223 return self
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000224
225 def __exit__(self, exc_type, exc_value, tb):
226 if exc_type is None:
227 try:
228 exc_name = self.expected.__name__
229 except AttributeError:
230 exc_name = str(self.expected)
231 if self.obj_name:
Ezio Melottib4dc2502011-05-06 15:01:41 +0300232 self._raiseFailure("{} not raised by {}".format(exc_name,
233 self.obj_name))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000234 else:
Ezio Melottib4dc2502011-05-06 15:01:41 +0300235 self._raiseFailure("{} not raised".format(exc_name))
Antoine Pitrou96810222014-04-29 01:23:50 +0200236 else:
237 traceback.clear_frames(tb)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000238 if not issubclass(exc_type, self.expected):
239 # let unexpected exceptions pass through
240 return False
Ezio Melotti49008232010-02-08 21:57:48 +0000241 # store exception, without traceback, for later retrieval
242 self.exception = exc_value.with_traceback(None)
Ezio Melottied3a7d22010-12-01 02:32:32 +0000243 if self.expected_regex is None:
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000244 return True
245
Ezio Melottied3a7d22010-12-01 02:32:32 +0000246 expected_regex = self.expected_regex
247 if not expected_regex.search(str(exc_value)):
Ezio Melottib4dc2502011-05-06 15:01:41 +0300248 self._raiseFailure('"{}" does not match "{}"'.format(
249 expected_regex.pattern, str(exc_value)))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000250 return True
251
252
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000253class _AssertWarnsContext(_AssertRaisesBaseContext):
254 """A context manager used to implement TestCase.assertWarns* methods."""
255
Serhiy Storchaka041dd8e2015-05-21 20:15:40 +0300256 _base_type = Warning
257 _base_type_str = 'a warning type or tuple of warning types'
258
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000259 def __enter__(self):
260 # The __warningregistry__'s need to be in a pristine state for tests
261 # to work properly.
262 for v in sys.modules.values():
263 if getattr(v, '__warningregistry__', None):
264 v.__warningregistry__ = {}
265 self.warnings_manager = warnings.catch_warnings(record=True)
266 self.warnings = self.warnings_manager.__enter__()
267 warnings.simplefilter("always", self.expected)
268 return self
269
270 def __exit__(self, exc_type, exc_value, tb):
271 self.warnings_manager.__exit__(exc_type, exc_value, tb)
272 if exc_type is not None:
273 # let unexpected exceptions pass through
274 return
275 try:
276 exc_name = self.expected.__name__
277 except AttributeError:
278 exc_name = str(self.expected)
279 first_matching = None
280 for m in self.warnings:
281 w = m.message
282 if not isinstance(w, self.expected):
283 continue
284 if first_matching is None:
285 first_matching = w
Ezio Melottied3a7d22010-12-01 02:32:32 +0000286 if (self.expected_regex is not None and
287 not self.expected_regex.search(str(w))):
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000288 continue
289 # store warning for later retrieval
290 self.warning = w
291 self.filename = m.filename
292 self.lineno = m.lineno
293 return
294 # Now we simply try to choose a helpful failure message
295 if first_matching is not None:
Ezio Melottib4dc2502011-05-06 15:01:41 +0300296 self._raiseFailure('"{}" does not match "{}"'.format(
297 self.expected_regex.pattern, str(first_matching)))
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000298 if self.obj_name:
Ezio Melottib4dc2502011-05-06 15:01:41 +0300299 self._raiseFailure("{} not triggered by {}".format(exc_name,
300 self.obj_name))
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000301 else:
Ezio Melottib4dc2502011-05-06 15:01:41 +0300302 self._raiseFailure("{} not triggered".format(exc_name))
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000303
304
Antoine Pitrou0715b9f2013-09-14 19:45:47 +0200305
306_LoggingWatcher = collections.namedtuple("_LoggingWatcher",
307 ["records", "output"])
308
309
310class _CapturingHandler(logging.Handler):
311 """
312 A logging handler capturing all (raw and formatted) logging output.
313 """
314
315 def __init__(self):
316 logging.Handler.__init__(self)
317 self.watcher = _LoggingWatcher([], [])
318
319 def flush(self):
320 pass
321
322 def emit(self, record):
323 self.watcher.records.append(record)
324 msg = self.format(record)
325 self.watcher.output.append(msg)
326
327
328
329class _AssertLogsContext(_BaseTestCaseContext):
330 """A context manager used to implement TestCase.assertLogs()."""
331
332 LOGGING_FORMAT = "%(levelname)s:%(name)s:%(message)s"
333
334 def __init__(self, test_case, logger_name, level):
335 _BaseTestCaseContext.__init__(self, test_case)
336 self.logger_name = logger_name
337 if level:
338 self.level = logging._nameToLevel.get(level, level)
339 else:
340 self.level = logging.INFO
341 self.msg = None
342
343 def __enter__(self):
344 if isinstance(self.logger_name, logging.Logger):
345 logger = self.logger = self.logger_name
346 else:
347 logger = self.logger = logging.getLogger(self.logger_name)
348 formatter = logging.Formatter(self.LOGGING_FORMAT)
349 handler = _CapturingHandler()
350 handler.setFormatter(formatter)
351 self.watcher = handler.watcher
352 self.old_handlers = logger.handlers[:]
353 self.old_level = logger.level
354 self.old_propagate = logger.propagate
355 logger.handlers = [handler]
356 logger.setLevel(self.level)
357 logger.propagate = False
358 return handler.watcher
359
360 def __exit__(self, exc_type, exc_value, tb):
361 self.logger.handlers = self.old_handlers
362 self.logger.propagate = self.old_propagate
363 self.logger.setLevel(self.old_level)
364 if exc_type is not None:
365 # let unexpected exceptions pass through
366 return False
367 if len(self.watcher.records) == 0:
368 self._raiseFailure(
369 "no logs of level {} or higher triggered on {}"
370 .format(logging.getLevelName(self.level), self.logger.name))
371
372
Serhiy Storchaka48fbe522017-06-23 21:47:39 +0300373class _OrderedChainMap(collections.ChainMap):
374 def __iter__(self):
375 seen = set()
376 for mapping in self.maps:
377 for k in mapping:
378 if k not in seen:
379 seen.add(k)
380 yield k
381
382
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000383class TestCase(object):
384 """A class whose instances are single test cases.
385
386 By default, the test code itself should be placed in a method named
387 'runTest'.
388
389 If the fixture may be used for many test cases, create as
390 many test methods as are needed. When instantiating such a TestCase
391 subclass, specify in the constructor arguments the name of the test method
392 that the instance is to execute.
393
394 Test authors should subclass TestCase for their own tests. Construction
395 and deconstruction of the test's environment ('fixture') can be
396 implemented by overriding the 'setUp' and 'tearDown' methods respectively.
397
398 If it is necessary to override the __init__ method, the base class
399 __init__ method must always be called. It is important that subclasses
400 should not change the signature of their __init__ method, since instances
401 of the classes are instantiated automatically by parts of the framework
402 in order to be run.
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000403
Ezio Melotti31797e52013-03-29 03:42:29 +0200404 When subclassing TestCase, you can set these attributes:
405 * failureException: determines which exception will be raised when
406 the instance's assertion methods fail; test methods raising this
407 exception will be deemed to have 'failed' rather than 'errored'.
408 * longMessage: determines whether long messages (including repr of
409 objects used in assert methods) will be printed on failure in *addition*
410 to any explicit message passed.
411 * maxDiff: sets the maximum length of a diff in failure messages
412 by assert methods using difflib. It is looked up as an instance
413 attribute so can be configured by individual tests if required.
414 """
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000415
416 failureException = AssertionError
417
Michael Foord5074df62010-12-03 00:53:09 +0000418 longMessage = True
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000419
Michael Foord085dfd32010-06-05 12:17:02 +0000420 maxDiff = 80*8
421
Ezio Melottiedd117f2011-04-27 10:20:38 +0300422 # If a string is longer than _diffThreshold, use normal comparison instead
423 # of difflib. See #11763.
424 _diffThreshold = 2**16
425
Benjamin Peterson847a4112010-03-14 15:04:17 +0000426 # Attribute used by TestSuite for classSetUp
427
428 _classSetupFailed = False
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000429
Lisa Roach0f221d02018-11-08 18:34:33 -0800430 _class_cleanups = []
431
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000432 def __init__(self, methodName='runTest'):
433 """Create an instance of the class that will use the named test
434 method when executed. Raises a ValueError if the instance does
435 not have a method with the specified name.
436 """
437 self._testMethodName = methodName
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100438 self._outcome = None
Michael Foord32e1d832011-01-03 17:00:11 +0000439 self._testMethodDoc = 'No test'
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000440 try:
441 testMethod = getattr(self, methodName)
442 except AttributeError:
Michael Foord32e1d832011-01-03 17:00:11 +0000443 if methodName != 'runTest':
444 # we allow instantiation with no explicit method name
445 # but not an *incorrect* or missing method name
446 raise ValueError("no such test method in %s: %s" %
447 (self.__class__, methodName))
448 else:
449 self._testMethodDoc = testMethod.__doc__
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000450 self._cleanups = []
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100451 self._subtest = None
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000452
453 # Map types to custom assertEqual functions that will compare
454 # instances of said type in more detail to generate a more useful
455 # error message.
Benjamin Peterson34b2b262011-07-12 19:21:42 -0500456 self._type_equality_funcs = {}
Michael Foord8ca6d982010-11-20 15:34:26 +0000457 self.addTypeEqualityFunc(dict, 'assertDictEqual')
458 self.addTypeEqualityFunc(list, 'assertListEqual')
459 self.addTypeEqualityFunc(tuple, 'assertTupleEqual')
460 self.addTypeEqualityFunc(set, 'assertSetEqual')
461 self.addTypeEqualityFunc(frozenset, 'assertSetEqual')
462 self.addTypeEqualityFunc(str, 'assertMultiLineEqual')
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000463
464 def addTypeEqualityFunc(self, typeobj, function):
465 """Add a type specific assertEqual style function to compare a type.
466
467 This method is for use by TestCase subclasses that need to register
468 their own type equality functions to provide nicer error messages.
469
470 Args:
471 typeobj: The data type to call this function on when both values
472 are of the same type in assertEqual().
473 function: The callable taking two arguments and an optional
474 msg= argument that raises self.failureException with a
475 useful error message when the two arguments are not equal.
476 """
Benjamin Peterson8f326b22009-12-13 02:10:36 +0000477 self._type_equality_funcs[typeobj] = function
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000478
Serhiy Storchaka42a139e2019-04-01 09:16:35 +0300479 def addCleanup(*args, **kwargs):
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000480 """Add a function, with arguments, to be called when the test is
481 completed. Functions added are called on a LIFO basis and are
482 called after tearDown on test failure or success.
483
484 Cleanup items are called even if setUp fails (unlike tearDown)."""
Serhiy Storchaka42a139e2019-04-01 09:16:35 +0300485 if len(args) >= 2:
486 self, function, *args = args
487 elif not args:
488 raise TypeError("descriptor 'addCleanup' of 'TestCase' object "
489 "needs an argument")
490 elif 'function' in kwargs:
491 function = kwargs.pop('function')
492 self, *args = args
493 import warnings
494 warnings.warn("Passing 'function' as keyword argument is deprecated",
495 DeprecationWarning, stacklevel=2)
496 else:
497 raise TypeError('addCleanup expected at least 1 positional '
498 'argument, got %d' % (len(args)-1))
499 args = tuple(args)
500
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000501 self._cleanups.append((function, args, kwargs))
Serhiy Storchakad53cf992019-05-06 22:40:27 +0300502 addCleanup.__text_signature__ = '($self, function, /, *args, **kwargs)'
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000503
Serhiy Storchaka42a139e2019-04-01 09:16:35 +0300504 def addClassCleanup(*args, **kwargs):
Lisa Roach0f221d02018-11-08 18:34:33 -0800505 """Same as addCleanup, except the cleanup items are called even if
506 setUpClass fails (unlike tearDownClass)."""
Serhiy Storchaka42a139e2019-04-01 09:16:35 +0300507 if len(args) >= 2:
508 cls, function, *args = args
509 elif not args:
510 raise TypeError("descriptor 'addClassCleanup' of 'TestCase' object "
511 "needs an argument")
512 else:
513 raise TypeError('addClassCleanup expected at least 1 positional '
514 'argument, got %d' % (len(args)-1))
515 args = tuple(args)
516
Lisa Roach0f221d02018-11-08 18:34:33 -0800517 cls._class_cleanups.append((function, args, kwargs))
Serhiy Storchakad53cf992019-05-06 22:40:27 +0300518 addClassCleanup.__text_signature__ = '($cls, function, /, *args, **kwargs)'
519 addClassCleanup = classmethod(addClassCleanup)
Lisa Roach0f221d02018-11-08 18:34:33 -0800520
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000521 def setUp(self):
522 "Hook method for setting up the test fixture before exercising it."
523 pass
524
525 def tearDown(self):
526 "Hook method for deconstructing the test fixture after testing it."
527 pass
528
Benjamin Peterson847a4112010-03-14 15:04:17 +0000529 @classmethod
530 def setUpClass(cls):
531 "Hook method for setting up class fixture before running tests in the class."
532
533 @classmethod
534 def tearDownClass(cls):
535 "Hook method for deconstructing the class fixture after running all tests in the class."
536
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000537 def countTestCases(self):
538 return 1
539
540 def defaultTestResult(self):
541 return result.TestResult()
542
543 def shortDescription(self):
Michael Foord34c94622010-02-10 15:51:42 +0000544 """Returns a one-line description of the test, or None if no
545 description has been provided.
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000546
Michael Foord34c94622010-02-10 15:51:42 +0000547 The default implementation of this method returns the first line of
548 the specified test method's docstring.
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000549 """
Michael Foord34c94622010-02-10 15:51:42 +0000550 doc = self._testMethodDoc
551 return doc and doc.split("\n")[0].strip() or None
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000552
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000553
554 def id(self):
Benjamin Peterson847a4112010-03-14 15:04:17 +0000555 return "%s.%s" % (strclass(self.__class__), self._testMethodName)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000556
557 def __eq__(self, other):
558 if type(self) is not type(other):
559 return NotImplemented
560
561 return self._testMethodName == other._testMethodName
562
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000563 def __hash__(self):
564 return hash((type(self), self._testMethodName))
565
566 def __str__(self):
Benjamin Peterson847a4112010-03-14 15:04:17 +0000567 return "%s (%s)" % (self._testMethodName, strclass(self.__class__))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000568
569 def __repr__(self):
570 return "<%s testMethod=%s>" % \
Benjamin Peterson847a4112010-03-14 15:04:17 +0000571 (strclass(self.__class__), self._testMethodName)
572
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100573 def _addSkip(self, result, test_case, reason):
Benjamin Peterson847a4112010-03-14 15:04:17 +0000574 addSkip = getattr(result, 'addSkip', None)
575 if addSkip is not None:
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100576 addSkip(test_case, reason)
Benjamin Peterson847a4112010-03-14 15:04:17 +0000577 else:
578 warnings.warn("TestResult has no addSkip method, skips not reported",
579 RuntimeWarning, 2)
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100580 result.addSuccess(test_case)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000581
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100582 @contextlib.contextmanager
Berker Peksag16ea19f2016-09-21 19:34:15 +0300583 def subTest(self, msg=_subtest_msg_sentinel, **params):
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100584 """Return a context manager that will return the enclosed block
585 of code in a subtest identified by the optional message and
586 keyword parameters. A failure in the subtest marks the test
587 case as failed but resumes execution at the end of the enclosed
588 block, allowing further test code to be executed.
589 """
Bruno Oliveirada2bf9f2018-10-12 07:35:55 -0300590 if self._outcome is None or not self._outcome.result_supports_subtests:
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100591 yield
592 return
593 parent = self._subtest
594 if parent is None:
Serhiy Storchaka48fbe522017-06-23 21:47:39 +0300595 params_map = _OrderedChainMap(params)
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100596 else:
597 params_map = parent.params.new_child(params)
598 self._subtest = _SubTest(self, msg, params_map)
Michael Foordb3468f72010-12-19 03:19:47 +0000599 try:
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100600 with self._outcome.testPartExecutor(self._subtest, isTest=True):
601 yield
602 if not self._outcome.success:
603 result = self._outcome.result
604 if result is not None and result.failfast:
605 raise _ShouldStop
606 elif self._outcome.expectedFailure:
607 # If the test is expecting a failure, we really want to
608 # stop now and register the expected failure.
609 raise _ShouldStop
610 finally:
611 self._subtest = parent
612
613 def _feedErrorsToResult(self, result, errors):
614 for test, exc_info in errors:
615 if isinstance(test, _SubTest):
616 result.addSubTest(test.test_case, test, exc_info)
617 elif exc_info is not None:
618 if issubclass(exc_info[0], self.failureException):
619 result.addFailure(test, exc_info)
620 else:
621 result.addError(test, exc_info)
622
623 def _addExpectedFailure(self, result, exc_info):
624 try:
625 addExpectedFailure = result.addExpectedFailure
626 except AttributeError:
627 warnings.warn("TestResult has no addExpectedFailure method, reporting as passes",
628 RuntimeWarning)
629 result.addSuccess(self)
630 else:
631 addExpectedFailure(self, exc_info)
632
633 def _addUnexpectedSuccess(self, result):
634 try:
635 addUnexpectedSuccess = result.addUnexpectedSuccess
636 except AttributeError:
637 warnings.warn("TestResult has no addUnexpectedSuccess method, reporting as failure",
638 RuntimeWarning)
639 # We need to pass an actual exception and traceback to addFailure,
640 # otherwise the legacy result can choke.
641 try:
642 raise _UnexpectedSuccess from None
643 except _UnexpectedSuccess:
644 result.addFailure(self, sys.exc_info())
645 else:
646 addUnexpectedSuccess(self)
Michael Foordb3468f72010-12-19 03:19:47 +0000647
Andrew Svetlov4dd3e3f2019-05-29 12:33:59 +0300648 def _callSetUp(self):
649 self.setUp()
650
651 def _callTestMethod(self, method):
652 method()
653
654 def _callTearDown(self):
655 self.tearDown()
656
657 def _callCleanup(self, function, /, *args, **kwargs):
658 function(*args, **kwargs)
659
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000660 def run(self, result=None):
661 orig_result = result
662 if result is None:
663 result = self.defaultTestResult()
664 startTestRun = getattr(result, 'startTestRun', None)
665 if startTestRun is not None:
666 startTestRun()
667
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000668 result.startTest(self)
Benjamin Peterson847a4112010-03-14 15:04:17 +0000669
670 testMethod = getattr(self, self._testMethodName)
671 if (getattr(self.__class__, "__unittest_skip__", False) or
672 getattr(testMethod, "__unittest_skip__", False)):
673 # If the class or method was skipped.
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000674 try:
Benjamin Peterson847a4112010-03-14 15:04:17 +0000675 skip_why = (getattr(self.__class__, '__unittest_skip_why__', '')
676 or getattr(testMethod, '__unittest_skip_why__', ''))
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100677 self._addSkip(result, self, skip_why)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000678 finally:
679 result.stopTest(self)
680 return
Robert Collinsed599b72015-08-28 10:34:51 +1200681 expecting_failure_method = getattr(testMethod,
682 "__unittest_expecting_failure__", False)
683 expecting_failure_class = getattr(self,
684 "__unittest_expecting_failure__", False)
685 expecting_failure = expecting_failure_class or expecting_failure_method
Victor Stinner031bd532013-12-09 01:52:50 +0100686 outcome = _Outcome(result)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000687 try:
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100688 self._outcome = outcome
Michael Foordb3468f72010-12-19 03:19:47 +0000689
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100690 with outcome.testPartExecutor(self):
Andrew Svetlov4dd3e3f2019-05-29 12:33:59 +0300691 self._callSetUp()
Michael Foordb3468f72010-12-19 03:19:47 +0000692 if outcome.success:
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100693 outcome.expecting_failure = expecting_failure
694 with outcome.testPartExecutor(self, isTest=True):
Andrew Svetlov4dd3e3f2019-05-29 12:33:59 +0300695 self._callTestMethod(testMethod)
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100696 outcome.expecting_failure = False
697 with outcome.testPartExecutor(self):
Andrew Svetlov4dd3e3f2019-05-29 12:33:59 +0300698 self._callTearDown()
Michael Foordb3468f72010-12-19 03:19:47 +0000699
700 self.doCleanups()
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100701 for test, reason in outcome.skipped:
702 self._addSkip(result, test, reason)
703 self._feedErrorsToResult(result, outcome.errors)
Michael Foordb3468f72010-12-19 03:19:47 +0000704 if outcome.success:
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100705 if expecting_failure:
706 if outcome.expectedFailure:
707 self._addExpectedFailure(result, outcome.expectedFailure)
Benjamin Peterson847a4112010-03-14 15:04:17 +0000708 else:
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100709 self._addUnexpectedSuccess(result)
710 else:
711 result.addSuccess(self)
Michael Foord1341bb02011-03-14 19:01:46 -0400712 return result
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000713 finally:
714 result.stopTest(self)
715 if orig_result is None:
716 stopTestRun = getattr(result, 'stopTestRun', None)
717 if stopTestRun is not None:
718 stopTestRun()
719
Victor Stinner031bd532013-12-09 01:52:50 +0100720 # explicitly break reference cycles:
721 # outcome.errors -> frame -> outcome -> outcome.errors
722 # outcome.expectedFailure -> frame -> outcome -> outcome.expectedFailure
723 outcome.errors.clear()
724 outcome.expectedFailure = None
725
726 # clear the outcome, no more needed
727 self._outcome = None
728
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000729 def doCleanups(self):
730 """Execute all cleanup functions. Normally called for you after
731 tearDown."""
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100732 outcome = self._outcome or _Outcome()
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000733 while self._cleanups:
Michael Foordb3468f72010-12-19 03:19:47 +0000734 function, args, kwargs = self._cleanups.pop()
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +0100735 with outcome.testPartExecutor(self):
Andrew Svetlov4dd3e3f2019-05-29 12:33:59 +0300736 self._callCleanup(function, *args, **kwargs)
Michael Foordb3468f72010-12-19 03:19:47 +0000737
738 # return this for backwards compatibility
Lisa Roach0f221d02018-11-08 18:34:33 -0800739 # even though we no longer use it internally
Michael Foordb3468f72010-12-19 03:19:47 +0000740 return outcome.success
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000741
Lisa Roach0f221d02018-11-08 18:34:33 -0800742 @classmethod
743 def doClassCleanups(cls):
744 """Execute all class cleanup functions. Normally called for you after
745 tearDownClass."""
746 cls.tearDown_exceptions = []
747 while cls._class_cleanups:
748 function, args, kwargs = cls._class_cleanups.pop()
749 try:
750 function(*args, **kwargs)
751 except Exception as exc:
752 cls.tearDown_exceptions.append(sys.exc_info())
753
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000754 def __call__(self, *args, **kwds):
755 return self.run(*args, **kwds)
756
757 def debug(self):
758 """Run the test without collecting errors in a TestResult"""
759 self.setUp()
760 getattr(self, self._testMethodName)()
761 self.tearDown()
Michael Foordb8748742010-06-10 16:16:08 +0000762 while self._cleanups:
763 function, args, kwargs = self._cleanups.pop(-1)
764 function(*args, **kwargs)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000765
766 def skipTest(self, reason):
767 """Skip this test."""
768 raise SkipTest(reason)
769
770 def fail(self, msg=None):
771 """Fail immediately, with the given message."""
772 raise self.failureException(msg)
773
774 def assertFalse(self, expr, msg=None):
Ezio Melotti3044fa72010-12-18 17:31:58 +0000775 """Check that the expression is false."""
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000776 if expr:
Ezio Melotti3044fa72010-12-18 17:31:58 +0000777 msg = self._formatMessage(msg, "%s is not false" % safe_repr(expr))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000778 raise self.failureException(msg)
779
780 def assertTrue(self, expr, msg=None):
Ezio Melotti3044fa72010-12-18 17:31:58 +0000781 """Check that the expression is true."""
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000782 if not expr:
Ezio Melotti3044fa72010-12-18 17:31:58 +0000783 msg = self._formatMessage(msg, "%s is not true" % safe_repr(expr))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000784 raise self.failureException(msg)
785
786 def _formatMessage(self, msg, standardMsg):
787 """Honour the longMessage attribute when generating failure messages.
788 If longMessage is False this means:
789 * Use only an explicit message if it is provided
790 * Otherwise use the standard message for the assert
791
792 If longMessage is True:
793 * Use the standard message
794 * If an explicit message is provided, plus ' : ' and the explicit message
795 """
796 if not self.longMessage:
797 return msg or standardMsg
798 if msg is None:
799 return standardMsg
Benjamin Peterson847a4112010-03-14 15:04:17 +0000800 try:
801 # don't switch to '{}' formatting in Python 2.X
802 # it changes the way unicode input is handled
803 return '%s : %s' % (standardMsg, msg)
804 except UnicodeDecodeError:
805 return '%s : %s' % (safe_repr(standardMsg), safe_repr(msg))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000806
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300807 def assertRaises(self, expected_exception, *args, **kwargs):
808 """Fail unless an exception of class expected_exception is raised
809 by the callable when invoked with specified positional and
810 keyword arguments. If a different type of exception is
Andrew Svetlov737fb892012-12-18 21:14:22 +0200811 raised, it will not be caught, and the test case will be
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000812 deemed to have suffered an error, exactly as for an
813 unexpected exception.
814
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300815 If called with the callable and arguments omitted, will return a
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000816 context object used like this::
817
Michael Foord1c42b122010-02-05 22:58:21 +0000818 with self.assertRaises(SomeException):
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000819 do_something()
Michael Foord1c42b122010-02-05 22:58:21 +0000820
Ezio Melottib4dc2502011-05-06 15:01:41 +0300821 An optional keyword argument 'msg' can be provided when assertRaises
822 is used as a context object.
823
Michael Foord1c42b122010-02-05 22:58:21 +0000824 The context manager keeps a reference to the exception as
Ezio Melotti49008232010-02-08 21:57:48 +0000825 the 'exception' attribute. This allows you to inspect the
Michael Foord1c42b122010-02-05 22:58:21 +0000826 exception after the assertion::
827
828 with self.assertRaises(SomeException) as cm:
829 do_something()
Ezio Melotti49008232010-02-08 21:57:48 +0000830 the_exception = cm.exception
Michael Foordb57ac6d2010-02-05 23:26:29 +0000831 self.assertEqual(the_exception.error_code, 3)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000832 """
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300833 context = _AssertRaisesContext(expected_exception, self)
Victor Stinnerbbd3cf82017-03-28 00:56:28 +0200834 try:
835 return context.handle('assertRaises', args, kwargs)
836 finally:
837 # bpo-23890: manually break a reference cycle
838 context = None
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000839
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300840 def assertWarns(self, expected_warning, *args, **kwargs):
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000841 """Fail unless a warning of class warnClass is triggered
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300842 by the callable when invoked with specified positional and
843 keyword arguments. If a different type of warning is
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000844 triggered, it will not be handled: depending on the other
845 warning filtering rules in effect, it might be silenced, printed
846 out, or raised as an exception.
847
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300848 If called with the callable and arguments omitted, will return a
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000849 context object used like this::
850
851 with self.assertWarns(SomeWarning):
852 do_something()
853
Ezio Melottib4dc2502011-05-06 15:01:41 +0300854 An optional keyword argument 'msg' can be provided when assertWarns
855 is used as a context object.
856
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000857 The context manager keeps a reference to the first matching
858 warning as the 'warning' attribute; similarly, the 'filename'
859 and 'lineno' attributes give you information about the line
860 of Python code from which the warning was triggered.
861 This allows you to inspect the warning after the assertion::
862
863 with self.assertWarns(SomeWarning) as cm:
864 do_something()
865 the_warning = cm.warning
866 self.assertEqual(the_warning.some_attribute, 147)
867 """
Serhiy Storchakadf573d62015-05-16 16:29:50 +0300868 context = _AssertWarnsContext(expected_warning, self)
869 return context.handle('assertWarns', args, kwargs)
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000870
Antoine Pitrou0715b9f2013-09-14 19:45:47 +0200871 def assertLogs(self, logger=None, level=None):
872 """Fail unless a log message of level *level* or higher is emitted
873 on *logger_name* or its children. If omitted, *level* defaults to
874 INFO and *logger* defaults to the root logger.
875
876 This method must be used as a context manager, and will yield
877 a recording object with two attributes: `output` and `records`.
878 At the end of the context manager, the `output` attribute will
879 be a list of the matching formatted log messages and the
880 `records` attribute will be a list of the corresponding LogRecord
881 objects.
882
883 Example::
884
885 with self.assertLogs('foo', level='INFO') as cm:
886 logging.getLogger('foo').info('first message')
887 logging.getLogger('foo.bar').error('second message')
888 self.assertEqual(cm.output, ['INFO:foo:first message',
889 'ERROR:foo.bar:second message'])
890 """
891 return _AssertLogsContext(self, logger, level)
892
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000893 def _getAssertEqualityFunc(self, first, second):
894 """Get a detailed comparison function for the types of the two args.
895
896 Returns: A callable accepting (first, second, msg=None) that will
897 raise a failure exception if first != second with a useful human
898 readable error message for those types.
899 """
900 #
901 # NOTE(gregory.p.smith): I considered isinstance(first, type(second))
902 # and vice versa. I opted for the conservative approach in case
903 # subclasses are not intended to be compared in detail to their super
904 # class instances using a type equality func. This means testing
905 # subtypes won't automagically use the detailed comparison. Callers
906 # should use their type specific assertSpamEqual method to compare
907 # subclasses if the detailed comparison is desired and appropriate.
908 # See the discussion in http://bugs.python.org/issue2578.
909 #
910 if type(first) is type(second):
911 asserter = self._type_equality_funcs.get(type(first))
912 if asserter is not None:
Benjamin Peterson34b2b262011-07-12 19:21:42 -0500913 if isinstance(asserter, str):
914 asserter = getattr(self, asserter)
Benjamin Peterson8f326b22009-12-13 02:10:36 +0000915 return asserter
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000916
917 return self._baseAssertEqual
918
919 def _baseAssertEqual(self, first, second, msg=None):
920 """The default assertEqual implementation, not type specific."""
921 if not first == second:
Serhiy Storchaka77622f52013-09-23 23:07:00 +0300922 standardMsg = '%s != %s' % _common_shorten_repr(first, second)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000923 msg = self._formatMessage(msg, standardMsg)
924 raise self.failureException(msg)
925
926 def assertEqual(self, first, second, msg=None):
927 """Fail if the two objects are unequal as determined by the '=='
928 operator.
929 """
930 assertion_func = self._getAssertEqualityFunc(first, second)
931 assertion_func(first, second, msg=msg)
932
933 def assertNotEqual(self, first, second, msg=None):
Ezio Melotti90eea972012-11-08 11:08:39 +0200934 """Fail if the two objects are equal as determined by the '!='
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000935 operator.
936 """
937 if not first != second:
Benjamin Peterson847a4112010-03-14 15:04:17 +0000938 msg = self._formatMessage(msg, '%s == %s' % (safe_repr(first),
939 safe_repr(second)))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000940 raise self.failureException(msg)
941
Michael Foord321d0592010-11-02 13:44:51 +0000942 def assertAlmostEqual(self, first, second, places=None, msg=None,
Benjamin Petersonb48af542010-04-11 20:43:16 +0000943 delta=None):
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000944 """Fail if the two objects are unequal as determined by their
945 difference rounded to the given number of decimal places
Benjamin Petersonb48af542010-04-11 20:43:16 +0000946 (default 7) and comparing to zero, or by comparing that the
Ron032a6482017-10-18 20:01:23 +0300947 difference between the two objects is more than the given
948 delta.
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000949
950 Note that decimal places (from zero) are usually not the same
Martin Pantereb995702016-07-28 01:11:04 +0000951 as significant digits (measured from the most significant digit).
Benjamin Peterson4ac9ce42009-10-04 14:49:41 +0000952
953 If the two objects compare equal then they will automatically
954 compare almost equal.
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000955 """
Benjamin Peterson4ac9ce42009-10-04 14:49:41 +0000956 if first == second:
Benjamin Petersonb48af542010-04-11 20:43:16 +0000957 # shortcut
Benjamin Peterson4ac9ce42009-10-04 14:49:41 +0000958 return
Benjamin Petersonb48af542010-04-11 20:43:16 +0000959 if delta is not None and places is not None:
960 raise TypeError("specify delta or places not both")
961
Giampaolo Rodola5d7a8d02017-05-01 18:18:56 +0200962 diff = abs(first - second)
Benjamin Petersonb48af542010-04-11 20:43:16 +0000963 if delta is not None:
Giampaolo Rodola5d7a8d02017-05-01 18:18:56 +0200964 if diff <= delta:
Benjamin Petersonb48af542010-04-11 20:43:16 +0000965 return
966
Giampaolo Rodola5d7a8d02017-05-01 18:18:56 +0200967 standardMsg = '%s != %s within %s delta (%s difference)' % (
968 safe_repr(first),
969 safe_repr(second),
970 safe_repr(delta),
971 safe_repr(diff))
Benjamin Petersonb48af542010-04-11 20:43:16 +0000972 else:
973 if places is None:
974 places = 7
975
Giampaolo Rodola5d7a8d02017-05-01 18:18:56 +0200976 if round(diff, places) == 0:
Benjamin Petersonb48af542010-04-11 20:43:16 +0000977 return
978
Giampaolo Rodola5d7a8d02017-05-01 18:18:56 +0200979 standardMsg = '%s != %s within %r places (%s difference)' % (
980 safe_repr(first),
981 safe_repr(second),
982 places,
983 safe_repr(diff))
Benjamin Petersonb48af542010-04-11 20:43:16 +0000984 msg = self._formatMessage(msg, standardMsg)
985 raise self.failureException(msg)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000986
Michael Foord321d0592010-11-02 13:44:51 +0000987 def assertNotAlmostEqual(self, first, second, places=None, msg=None,
Benjamin Petersonb48af542010-04-11 20:43:16 +0000988 delta=None):
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000989 """Fail if the two objects are equal as determined by their
990 difference rounded to the given number of decimal places
Benjamin Petersonb48af542010-04-11 20:43:16 +0000991 (default 7) and comparing to zero, or by comparing that the
Ron032a6482017-10-18 20:01:23 +0300992 difference between the two objects is less than the given delta.
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000993
994 Note that decimal places (from zero) are usually not the same
Martin Pantereb995702016-07-28 01:11:04 +0000995 as significant digits (measured from the most significant digit).
Benjamin Peterson4ac9ce42009-10-04 14:49:41 +0000996
997 Objects that are equal automatically fail.
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000998 """
Benjamin Petersonb48af542010-04-11 20:43:16 +0000999 if delta is not None and places is not None:
1000 raise TypeError("specify delta or places not both")
Giampaolo Rodola5d7a8d02017-05-01 18:18:56 +02001001 diff = abs(first - second)
Benjamin Petersonb48af542010-04-11 20:43:16 +00001002 if delta is not None:
Giampaolo Rodola5d7a8d02017-05-01 18:18:56 +02001003 if not (first == second) and diff > delta:
Benjamin Petersonb48af542010-04-11 20:43:16 +00001004 return
Giampaolo Rodola5d7a8d02017-05-01 18:18:56 +02001005 standardMsg = '%s == %s within %s delta (%s difference)' % (
1006 safe_repr(first),
1007 safe_repr(second),
1008 safe_repr(delta),
1009 safe_repr(diff))
Benjamin Petersonb48af542010-04-11 20:43:16 +00001010 else:
1011 if places is None:
1012 places = 7
Giampaolo Rodola5d7a8d02017-05-01 18:18:56 +02001013 if not (first == second) and round(diff, places) != 0:
Benjamin Petersonb48af542010-04-11 20:43:16 +00001014 return
Benjamin Peterson847a4112010-03-14 15:04:17 +00001015 standardMsg = '%s == %s within %r places' % (safe_repr(first),
Benjamin Petersonb48af542010-04-11 20:43:16 +00001016 safe_repr(second),
1017 places)
1018
1019 msg = self._formatMessage(msg, standardMsg)
1020 raise self.failureException(msg)
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001021
Michael Foord085dfd32010-06-05 12:17:02 +00001022 def assertSequenceEqual(self, seq1, seq2, msg=None, seq_type=None):
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001023 """An equality assertion for ordered sequences (like lists and tuples).
1024
R. David Murrayad13f222010-01-29 22:17:58 +00001025 For the purposes of this function, a valid ordered sequence type is one
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001026 which can be indexed, has a length, and has an equality operator.
1027
1028 Args:
1029 seq1: The first sequence to compare.
1030 seq2: The second sequence to compare.
1031 seq_type: The expected datatype of the sequences, or None if no
1032 datatype should be enforced.
1033 msg: Optional message to use on failure instead of a list of
1034 differences.
1035 """
Benjamin Petersonb29614e2012-10-09 11:16:03 -04001036 if seq_type is not None:
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001037 seq_type_name = seq_type.__name__
1038 if not isinstance(seq1, seq_type):
Benjamin Peterson847a4112010-03-14 15:04:17 +00001039 raise self.failureException('First sequence is not a %s: %s'
1040 % (seq_type_name, safe_repr(seq1)))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001041 if not isinstance(seq2, seq_type):
Benjamin Peterson847a4112010-03-14 15:04:17 +00001042 raise self.failureException('Second sequence is not a %s: %s'
1043 % (seq_type_name, safe_repr(seq2)))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001044 else:
1045 seq_type_name = "sequence"
1046
1047 differing = None
1048 try:
1049 len1 = len(seq1)
1050 except (TypeError, NotImplementedError):
1051 differing = 'First %s has no length. Non-sequence?' % (
1052 seq_type_name)
1053
1054 if differing is None:
1055 try:
1056 len2 = len(seq2)
1057 except (TypeError, NotImplementedError):
1058 differing = 'Second %s has no length. Non-sequence?' % (
1059 seq_type_name)
1060
1061 if differing is None:
1062 if seq1 == seq2:
1063 return
1064
Serhiy Storchaka77622f52013-09-23 23:07:00 +03001065 differing = '%ss differ: %s != %s\n' % (
1066 (seq_type_name.capitalize(),) +
1067 _common_shorten_repr(seq1, seq2))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001068
1069 for i in range(min(len1, len2)):
1070 try:
1071 item1 = seq1[i]
1072 except (TypeError, IndexError, NotImplementedError):
1073 differing += ('\nUnable to index element %d of first %s\n' %
1074 (i, seq_type_name))
1075 break
1076
1077 try:
1078 item2 = seq2[i]
1079 except (TypeError, IndexError, NotImplementedError):
1080 differing += ('\nUnable to index element %d of second %s\n' %
1081 (i, seq_type_name))
1082 break
1083
1084 if item1 != item2:
1085 differing += ('\nFirst differing element %d:\n%s\n%s\n' %
Serhiy Storchaka685fbed2016-04-25 08:58:25 +03001086 ((i,) + _common_shorten_repr(item1, item2)))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001087 break
1088 else:
1089 if (len1 == len2 and seq_type is None and
1090 type(seq1) != type(seq2)):
1091 # The sequences are the same, but have differing types.
1092 return
1093
1094 if len1 > len2:
1095 differing += ('\nFirst %s contains %d additional '
1096 'elements.\n' % (seq_type_name, len1 - len2))
1097 try:
1098 differing += ('First extra element %d:\n%s\n' %
Serhiy Storchaka685fbed2016-04-25 08:58:25 +03001099 (len2, safe_repr(seq1[len2])))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001100 except (TypeError, IndexError, NotImplementedError):
1101 differing += ('Unable to index element %d '
1102 'of first %s\n' % (len2, seq_type_name))
1103 elif len1 < len2:
1104 differing += ('\nSecond %s contains %d additional '
1105 'elements.\n' % (seq_type_name, len2 - len1))
1106 try:
1107 differing += ('First extra element %d:\n%s\n' %
Serhiy Storchaka685fbed2016-04-25 08:58:25 +03001108 (len1, safe_repr(seq2[len1])))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001109 except (TypeError, IndexError, NotImplementedError):
1110 differing += ('Unable to index element %d '
1111 'of second %s\n' % (len1, seq_type_name))
Michael Foord2034d9a2010-06-05 11:27:52 +00001112 standardMsg = differing
1113 diffMsg = '\n' + '\n'.join(
Benjamin Peterson6e8c7572009-10-04 20:19:21 +00001114 difflib.ndiff(pprint.pformat(seq1).splitlines(),
1115 pprint.pformat(seq2).splitlines()))
Michael Foord085dfd32010-06-05 12:17:02 +00001116
1117 standardMsg = self._truncateMessage(standardMsg, diffMsg)
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001118 msg = self._formatMessage(msg, standardMsg)
1119 self.fail(msg)
1120
Michael Foord085dfd32010-06-05 12:17:02 +00001121 def _truncateMessage(self, message, diff):
1122 max_diff = self.maxDiff
1123 if max_diff is None or len(diff) <= max_diff:
1124 return message + diff
Michael Foord9dad32e2010-06-05 13:49:56 +00001125 return message + (DIFF_OMITTED % len(diff))
Michael Foord085dfd32010-06-05 12:17:02 +00001126
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001127 def assertListEqual(self, list1, list2, msg=None):
1128 """A list-specific equality assertion.
1129
1130 Args:
1131 list1: The first list to compare.
1132 list2: The second list to compare.
1133 msg: Optional message to use on failure instead of a list of
1134 differences.
1135
1136 """
1137 self.assertSequenceEqual(list1, list2, msg, seq_type=list)
1138
1139 def assertTupleEqual(self, tuple1, tuple2, msg=None):
1140 """A tuple-specific equality assertion.
1141
1142 Args:
1143 tuple1: The first tuple to compare.
1144 tuple2: The second tuple to compare.
1145 msg: Optional message to use on failure instead of a list of
1146 differences.
1147 """
1148 self.assertSequenceEqual(tuple1, tuple2, msg, seq_type=tuple)
1149
1150 def assertSetEqual(self, set1, set2, msg=None):
1151 """A set-specific equality assertion.
1152
1153 Args:
1154 set1: The first set to compare.
1155 set2: The second set to compare.
1156 msg: Optional message to use on failure instead of a list of
1157 differences.
1158
Michael Foord91c9da32010-03-20 17:21:27 +00001159 assertSetEqual uses ducktyping to support different types of sets, and
1160 is optimized for sets specifically (parameters must support a
1161 difference method).
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001162 """
1163 try:
1164 difference1 = set1.difference(set2)
1165 except TypeError as e:
1166 self.fail('invalid type when attempting set difference: %s' % e)
1167 except AttributeError as e:
1168 self.fail('first argument does not support set difference: %s' % e)
1169
1170 try:
1171 difference2 = set2.difference(set1)
1172 except TypeError as e:
1173 self.fail('invalid type when attempting set difference: %s' % e)
1174 except AttributeError as e:
1175 self.fail('second argument does not support set difference: %s' % e)
1176
1177 if not (difference1 or difference2):
1178 return
1179
1180 lines = []
1181 if difference1:
1182 lines.append('Items in the first set but not the second:')
1183 for item in difference1:
1184 lines.append(repr(item))
1185 if difference2:
1186 lines.append('Items in the second set but not the first:')
1187 for item in difference2:
1188 lines.append(repr(item))
1189
1190 standardMsg = '\n'.join(lines)
1191 self.fail(self._formatMessage(msg, standardMsg))
1192
1193 def assertIn(self, member, container, msg=None):
1194 """Just like self.assertTrue(a in b), but with a nicer default message."""
1195 if member not in container:
Benjamin Peterson847a4112010-03-14 15:04:17 +00001196 standardMsg = '%s not found in %s' % (safe_repr(member),
1197 safe_repr(container))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001198 self.fail(self._formatMessage(msg, standardMsg))
1199
1200 def assertNotIn(self, member, container, msg=None):
1201 """Just like self.assertTrue(a not in b), but with a nicer default message."""
1202 if member in container:
Benjamin Peterson847a4112010-03-14 15:04:17 +00001203 standardMsg = '%s unexpectedly found in %s' % (safe_repr(member),
1204 safe_repr(container))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001205 self.fail(self._formatMessage(msg, standardMsg))
1206
1207 def assertIs(self, expr1, expr2, msg=None):
1208 """Just like self.assertTrue(a is b), but with a nicer default message."""
1209 if expr1 is not expr2:
Benjamin Peterson847a4112010-03-14 15:04:17 +00001210 standardMsg = '%s is not %s' % (safe_repr(expr1),
1211 safe_repr(expr2))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001212 self.fail(self._formatMessage(msg, standardMsg))
1213
1214 def assertIsNot(self, expr1, expr2, msg=None):
1215 """Just like self.assertTrue(a is not b), but with a nicer default message."""
1216 if expr1 is expr2:
Benjamin Peterson847a4112010-03-14 15:04:17 +00001217 standardMsg = 'unexpectedly identical: %s' % (safe_repr(expr1),)
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001218 self.fail(self._formatMessage(msg, standardMsg))
1219
1220 def assertDictEqual(self, d1, d2, msg=None):
Ezio Melottib3aedd42010-11-20 19:04:17 +00001221 self.assertIsInstance(d1, dict, 'First argument is not a dictionary')
1222 self.assertIsInstance(d2, dict, 'Second argument is not a dictionary')
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001223
1224 if d1 != d2:
Serhiy Storchaka77622f52013-09-23 23:07:00 +03001225 standardMsg = '%s != %s' % _common_shorten_repr(d1, d2)
Michael Foord085dfd32010-06-05 12:17:02 +00001226 diff = ('\n' + '\n'.join(difflib.ndiff(
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001227 pprint.pformat(d1).splitlines(),
1228 pprint.pformat(d2).splitlines())))
Michael Foordcb11b252010-06-05 13:14:43 +00001229 standardMsg = self._truncateMessage(standardMsg, diff)
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001230 self.fail(self._formatMessage(msg, standardMsg))
1231
Ezio Melotti0f535012011-04-03 18:02:13 +03001232 def assertDictContainsSubset(self, subset, dictionary, msg=None):
1233 """Checks whether dictionary is a superset of subset."""
1234 warnings.warn('assertDictContainsSubset is deprecated',
1235 DeprecationWarning)
1236 missing = []
1237 mismatched = []
1238 for key, value in subset.items():
1239 if key not in dictionary:
1240 missing.append(key)
1241 elif value != dictionary[key]:
1242 mismatched.append('%s, expected: %s, actual: %s' %
1243 (safe_repr(key), safe_repr(value),
1244 safe_repr(dictionary[key])))
1245
1246 if not (missing or mismatched):
1247 return
1248
1249 standardMsg = ''
1250 if missing:
1251 standardMsg = 'Missing: %s' % ','.join(safe_repr(m) for m in
1252 missing)
1253 if mismatched:
1254 if standardMsg:
1255 standardMsg += '; '
1256 standardMsg += 'Mismatched values: %s' % ','.join(mismatched)
1257
1258 self.fail(self._formatMessage(msg, standardMsg))
1259
1260
Raymond Hettinger57bd00a2010-12-24 21:51:48 +00001261 def assertCountEqual(self, first, second, msg=None):
jkleint39baace2019-04-23 01:34:29 -07001262 """Asserts that two iterables have the same elements, the same number of
1263 times, without regard to order.
Michael Foord8442a602010-03-20 16:58:04 +00001264
Raymond Hettinger57bd00a2010-12-24 21:51:48 +00001265 self.assertEqual(Counter(list(first)),
1266 Counter(list(second)))
Michael Foord8442a602010-03-20 16:58:04 +00001267
Raymond Hettinger57bd00a2010-12-24 21:51:48 +00001268 Example:
Michael Foord8442a602010-03-20 16:58:04 +00001269 - [0, 1, 1] and [1, 0, 1] compare equal.
1270 - [0, 0, 1] and [0, 1] compare unequal.
Raymond Hettinger57bd00a2010-12-24 21:51:48 +00001271
Michael Foord8442a602010-03-20 16:58:04 +00001272 """
Michael Foorde180d392011-01-28 19:51:48 +00001273 first_seq, second_seq = list(first), list(second)
Michael Foord8442a602010-03-20 16:58:04 +00001274 try:
Michael Foorde180d392011-01-28 19:51:48 +00001275 first = collections.Counter(first_seq)
1276 second = collections.Counter(second_seq)
Michael Foord8442a602010-03-20 16:58:04 +00001277 except TypeError:
Raymond Hettinger6518f5e2010-12-24 00:52:54 +00001278 # Handle case with unhashable elements
Michael Foorde180d392011-01-28 19:51:48 +00001279 differences = _count_diff_all_purpose(first_seq, second_seq)
Michael Foord8442a602010-03-20 16:58:04 +00001280 else:
Michael Foorde180d392011-01-28 19:51:48 +00001281 if first == second:
Raymond Hettinger6e165b32010-11-27 09:31:37 +00001282 return
Michael Foorde180d392011-01-28 19:51:48 +00001283 differences = _count_diff_hashable(first_seq, second_seq)
Michael Foord8442a602010-03-20 16:58:04 +00001284
Raymond Hettinger93e233d2010-12-24 10:02:22 +00001285 if differences:
1286 standardMsg = 'Element counts were not equal:\n'
Raymond Hettinger57bd00a2010-12-24 21:51:48 +00001287 lines = ['First has %d, Second has %d: %r' % diff for diff in differences]
Raymond Hettinger93e233d2010-12-24 10:02:22 +00001288 diffMsg = '\n'.join(lines)
1289 standardMsg = self._truncateMessage(standardMsg, diffMsg)
1290 msg = self._formatMessage(msg, standardMsg)
1291 self.fail(msg)
Michael Foord8442a602010-03-20 16:58:04 +00001292
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001293 def assertMultiLineEqual(self, first, second, msg=None):
1294 """Assert that two multi-line strings are equal."""
Ezio Melottib3aedd42010-11-20 19:04:17 +00001295 self.assertIsInstance(first, str, 'First argument is not a string')
1296 self.assertIsInstance(second, str, 'Second argument is not a string')
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001297
1298 if first != second:
Ezio Melottiedd117f2011-04-27 10:20:38 +03001299 # don't use difflib if the strings are too long
1300 if (len(first) > self._diffThreshold or
1301 len(second) > self._diffThreshold):
1302 self._baseAssertEqual(first, second, msg)
Ezio Melottid8b509b2011-09-28 17:37:55 +03001303 firstlines = first.splitlines(keepends=True)
1304 secondlines = second.splitlines(keepends=True)
Michael Foordc653ce32010-07-10 13:52:22 +00001305 if len(firstlines) == 1 and first.strip('\r\n') == first:
1306 firstlines = [first + '\n']
1307 secondlines = [second + '\n']
Serhiy Storchaka77622f52013-09-23 23:07:00 +03001308 standardMsg = '%s != %s' % _common_shorten_repr(first, second)
Michael Foordc653ce32010-07-10 13:52:22 +00001309 diff = '\n' + ''.join(difflib.ndiff(firstlines, secondlines))
Michael Foordcb11b252010-06-05 13:14:43 +00001310 standardMsg = self._truncateMessage(standardMsg, diff)
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001311 self.fail(self._formatMessage(msg, standardMsg))
1312
1313 def assertLess(self, a, b, msg=None):
1314 """Just like self.assertTrue(a < b), but with a nicer default message."""
1315 if not a < b:
Benjamin Peterson847a4112010-03-14 15:04:17 +00001316 standardMsg = '%s not less than %s' % (safe_repr(a), safe_repr(b))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001317 self.fail(self._formatMessage(msg, standardMsg))
1318
1319 def assertLessEqual(self, a, b, msg=None):
1320 """Just like self.assertTrue(a <= b), but with a nicer default message."""
1321 if not a <= b:
Benjamin Peterson847a4112010-03-14 15:04:17 +00001322 standardMsg = '%s not less than or equal to %s' % (safe_repr(a), safe_repr(b))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001323 self.fail(self._formatMessage(msg, standardMsg))
1324
1325 def assertGreater(self, a, b, msg=None):
1326 """Just like self.assertTrue(a > b), but with a nicer default message."""
1327 if not a > b:
Benjamin Peterson847a4112010-03-14 15:04:17 +00001328 standardMsg = '%s not greater than %s' % (safe_repr(a), safe_repr(b))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001329 self.fail(self._formatMessage(msg, standardMsg))
1330
1331 def assertGreaterEqual(self, a, b, msg=None):
1332 """Just like self.assertTrue(a >= b), but with a nicer default message."""
1333 if not a >= b:
Benjamin Peterson847a4112010-03-14 15:04:17 +00001334 standardMsg = '%s not greater than or equal to %s' % (safe_repr(a), safe_repr(b))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001335 self.fail(self._formatMessage(msg, standardMsg))
1336
1337 def assertIsNone(self, obj, msg=None):
1338 """Same as self.assertTrue(obj is None), with a nicer default message."""
1339 if obj is not None:
Benjamin Peterson847a4112010-03-14 15:04:17 +00001340 standardMsg = '%s is not None' % (safe_repr(obj),)
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001341 self.fail(self._formatMessage(msg, standardMsg))
1342
1343 def assertIsNotNone(self, obj, msg=None):
1344 """Included for symmetry with assertIsNone."""
1345 if obj is None:
1346 standardMsg = 'unexpectedly None'
1347 self.fail(self._formatMessage(msg, standardMsg))
1348
Benjamin Peterson6e8c7572009-10-04 20:19:21 +00001349 def assertIsInstance(self, obj, cls, msg=None):
1350 """Same as self.assertTrue(isinstance(obj, cls)), with a nicer
1351 default message."""
1352 if not isinstance(obj, cls):
Benjamin Peterson847a4112010-03-14 15:04:17 +00001353 standardMsg = '%s is not an instance of %r' % (safe_repr(obj), cls)
Benjamin Peterson6e8c7572009-10-04 20:19:21 +00001354 self.fail(self._formatMessage(msg, standardMsg))
1355
1356 def assertNotIsInstance(self, obj, cls, msg=None):
1357 """Included for symmetry with assertIsInstance."""
1358 if isinstance(obj, cls):
Benjamin Peterson847a4112010-03-14 15:04:17 +00001359 standardMsg = '%s is an instance of %r' % (safe_repr(obj), cls)
Benjamin Peterson6e8c7572009-10-04 20:19:21 +00001360 self.fail(self._formatMessage(msg, standardMsg))
1361
Ezio Melottied3a7d22010-12-01 02:32:32 +00001362 def assertRaisesRegex(self, expected_exception, expected_regex,
Serhiy Storchakadf573d62015-05-16 16:29:50 +03001363 *args, **kwargs):
Ezio Melottied3a7d22010-12-01 02:32:32 +00001364 """Asserts that the message in a raised exception matches a regex.
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001365
1366 Args:
1367 expected_exception: Exception class expected to be raised.
Serhiy Storchaka0b5e61d2017-10-04 20:09:49 +03001368 expected_regex: Regex (re.Pattern object or string) expected
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001369 to be found in error message.
Serhiy Storchakadf573d62015-05-16 16:29:50 +03001370 args: Function to be called and extra positional args.
1371 kwargs: Extra kwargs.
Ezio Melottib4dc2502011-05-06 15:01:41 +03001372 msg: Optional message used in case of failure. Can only be used
1373 when assertRaisesRegex is used as a context manager.
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001374 """
Serhiy Storchakadf573d62015-05-16 16:29:50 +03001375 context = _AssertRaisesContext(expected_exception, self, expected_regex)
1376 return context.handle('assertRaisesRegex', args, kwargs)
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001377
Ezio Melottied3a7d22010-12-01 02:32:32 +00001378 def assertWarnsRegex(self, expected_warning, expected_regex,
Serhiy Storchakadf573d62015-05-16 16:29:50 +03001379 *args, **kwargs):
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +00001380 """Asserts that the message in a triggered warning matches a regexp.
1381 Basic functioning is similar to assertWarns() with the addition
1382 that only warnings whose messages also match the regular expression
1383 are considered successful matches.
1384
1385 Args:
1386 expected_warning: Warning class expected to be triggered.
Serhiy Storchaka0b5e61d2017-10-04 20:09:49 +03001387 expected_regex: Regex (re.Pattern object or string) expected
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +00001388 to be found in error message.
Serhiy Storchakadf573d62015-05-16 16:29:50 +03001389 args: Function to be called and extra positional args.
1390 kwargs: Extra kwargs.
Ezio Melottib4dc2502011-05-06 15:01:41 +03001391 msg: Optional message used in case of failure. Can only be used
1392 when assertWarnsRegex is used as a context manager.
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +00001393 """
Serhiy Storchakadf573d62015-05-16 16:29:50 +03001394 context = _AssertWarnsContext(expected_warning, self, expected_regex)
1395 return context.handle('assertWarnsRegex', args, kwargs)
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +00001396
Ezio Melottied3a7d22010-12-01 02:32:32 +00001397 def assertRegex(self, text, expected_regex, msg=None):
Michael Foorde3ef5f12010-05-08 16:46:14 +00001398 """Fail the test unless the text matches the regular expression."""
Ezio Melottied3a7d22010-12-01 02:32:32 +00001399 if isinstance(expected_regex, (str, bytes)):
Gregory P. Smithed16bf42010-12-16 19:23:05 +00001400 assert expected_regex, "expected_regex must not be empty."
Ezio Melottied3a7d22010-12-01 02:32:32 +00001401 expected_regex = re.compile(expected_regex)
1402 if not expected_regex.search(text):
Robert Collinsbe6caca2015-08-20 11:13:09 +12001403 standardMsg = "Regex didn't match: %r not found in %r" % (
1404 expected_regex.pattern, text)
1405 # _formatMessage ensures the longMessage option is respected
1406 msg = self._formatMessage(msg, standardMsg)
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001407 raise self.failureException(msg)
1408
Ezio Melotti8f776302010-12-10 02:32:05 +00001409 def assertNotRegex(self, text, unexpected_regex, msg=None):
Michael Foorde3ef5f12010-05-08 16:46:14 +00001410 """Fail the test if the text matches the regular expression."""
Ezio Melottied3a7d22010-12-01 02:32:32 +00001411 if isinstance(unexpected_regex, (str, bytes)):
1412 unexpected_regex = re.compile(unexpected_regex)
1413 match = unexpected_regex.search(text)
Benjamin Petersonb48af542010-04-11 20:43:16 +00001414 if match:
Robert Collinsbe6caca2015-08-20 11:13:09 +12001415 standardMsg = 'Regex matched: %r matches %r in %r' % (
1416 text[match.start() : match.end()],
1417 unexpected_regex.pattern,
1418 text)
1419 # _formatMessage ensures the longMessage option is respected
1420 msg = self._formatMessage(msg, standardMsg)
Benjamin Petersonb48af542010-04-11 20:43:16 +00001421 raise self.failureException(msg)
1422
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001423
Ezio Melottied3a7d22010-12-01 02:32:32 +00001424 def _deprecate(original_func):
1425 def deprecated_func(*args, **kwargs):
1426 warnings.warn(
1427 'Please use {0} instead.'.format(original_func.__name__),
1428 DeprecationWarning, 2)
1429 return original_func(*args, **kwargs)
1430 return deprecated_func
1431
Ezio Melotti361467e2011-04-03 17:37:58 +03001432 # see #9424
Ezio Melotti0f535012011-04-03 18:02:13 +03001433 failUnlessEqual = assertEquals = _deprecate(assertEqual)
1434 failIfEqual = assertNotEquals = _deprecate(assertNotEqual)
1435 failUnlessAlmostEqual = assertAlmostEquals = _deprecate(assertAlmostEqual)
1436 failIfAlmostEqual = assertNotAlmostEquals = _deprecate(assertNotAlmostEqual)
1437 failUnless = assert_ = _deprecate(assertTrue)
1438 failUnlessRaises = _deprecate(assertRaises)
1439 failIf = _deprecate(assertFalse)
Ezio Melottied3a7d22010-12-01 02:32:32 +00001440 assertRaisesRegexp = _deprecate(assertRaisesRegex)
1441 assertRegexpMatches = _deprecate(assertRegex)
Robert Collinsbe6caca2015-08-20 11:13:09 +12001442 assertNotRegexpMatches = _deprecate(assertNotRegex)
Ezio Melottied3a7d22010-12-01 02:32:32 +00001443
1444
1445
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001446class FunctionTestCase(TestCase):
1447 """A test case that wraps a test function.
1448
1449 This is useful for slipping pre-existing test functions into the
1450 unittest framework. Optionally, set-up and tidy-up functions can be
1451 supplied. As with TestCase, the tidy-up ('tearDown') function will
1452 always be called if the set-up ('setUp') function ran successfully.
1453 """
1454
1455 def __init__(self, testFunc, setUp=None, tearDown=None, description=None):
1456 super(FunctionTestCase, self).__init__()
1457 self._setUpFunc = setUp
1458 self._tearDownFunc = tearDown
1459 self._testFunc = testFunc
1460 self._description = description
1461
1462 def setUp(self):
1463 if self._setUpFunc is not None:
1464 self._setUpFunc()
1465
1466 def tearDown(self):
1467 if self._tearDownFunc is not None:
1468 self._tearDownFunc()
1469
1470 def runTest(self):
1471 self._testFunc()
1472
1473 def id(self):
1474 return self._testFunc.__name__
1475
1476 def __eq__(self, other):
1477 if not isinstance(other, self.__class__):
1478 return NotImplemented
1479
1480 return self._setUpFunc == other._setUpFunc and \
1481 self._tearDownFunc == other._tearDownFunc and \
1482 self._testFunc == other._testFunc and \
1483 self._description == other._description
1484
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001485 def __hash__(self):
1486 return hash((type(self), self._setUpFunc, self._tearDownFunc,
1487 self._testFunc, self._description))
1488
1489 def __str__(self):
Benjamin Peterson847a4112010-03-14 15:04:17 +00001490 return "%s (%s)" % (strclass(self.__class__),
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001491 self._testFunc.__name__)
1492
1493 def __repr__(self):
Benjamin Peterson847a4112010-03-14 15:04:17 +00001494 return "<%s tec=%s>" % (strclass(self.__class__),
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001495 self._testFunc)
1496
1497 def shortDescription(self):
1498 if self._description is not None:
1499 return self._description
1500 doc = self._testFunc.__doc__
1501 return doc and doc.split("\n")[0].strip() or None
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +01001502
1503
1504class _SubTest(TestCase):
1505
1506 def __init__(self, test_case, message, params):
1507 super().__init__()
1508 self._message = message
1509 self.test_case = test_case
1510 self.params = params
1511 self.failureException = test_case.failureException
1512
1513 def runTest(self):
1514 raise NotImplementedError("subtests cannot be run directly")
1515
1516 def _subDescription(self):
1517 parts = []
Berker Peksag16ea19f2016-09-21 19:34:15 +03001518 if self._message is not _subtest_msg_sentinel:
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +01001519 parts.append("[{}]".format(self._message))
1520 if self.params:
1521 params_desc = ', '.join(
1522 "{}={!r}".format(k, v)
Serhiy Storchaka48fbe522017-06-23 21:47:39 +03001523 for (k, v) in self.params.items())
Antoine Pitrouc9b3ef22013-03-20 20:16:47 +01001524 parts.append("({})".format(params_desc))
1525 return " ".join(parts) or '(<subtest>)'
1526
1527 def id(self):
1528 return "{} {}".format(self.test_case.id(), self._subDescription())
1529
1530 def shortDescription(self):
1531 """Returns a one-line description of the subtest, or None if no
1532 description has been provided.
1533 """
1534 return self.test_case.shortDescription()
1535
1536 def __str__(self):
1537 return "{} {}".format(self.test_case, self._subDescription())