blob: 5bed86857d7337b1ca383ee0108e7d827b100084 [file] [log] [blame]
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001"""Test case implementation"""
2
3import sys
4import functools
5import difflib
6import pprint
7import re
8import warnings
Raymond Hettinger6e165b32010-11-27 09:31:37 +00009import collections
Benjamin Petersonbed7d042009-07-19 21:01:52 +000010
Benjamin Peterson847a4112010-03-14 15:04:17 +000011from . import result
Florent Xiclunac53ae582011-11-04 08:25:54 +010012from .util import (strclass, safe_repr, _count_diff_all_purpose,
Raymond Hettinger93e233d2010-12-24 10:02:22 +000013 _count_diff_hashable)
Benjamin Petersonbed7d042009-07-19 21:01:52 +000014
Benjamin Petersondccc1fc2010-03-22 00:15:53 +000015__unittest = True
Benjamin Petersonbed7d042009-07-19 21:01:52 +000016
Michael Foord9dad32e2010-06-05 13:49:56 +000017
18DIFF_OMITTED = ('\nDiff is %s characters long. '
19 'Set self.maxDiff to None to see it.')
20
Benjamin Petersonbed7d042009-07-19 21:01:52 +000021class SkipTest(Exception):
22 """
23 Raise this exception in a test to skip it.
24
25 Usually you can use TestResult.skip() or one of the skipping decorators
26 instead of raising this directly.
27 """
Benjamin Petersonbed7d042009-07-19 21:01:52 +000028
29class _ExpectedFailure(Exception):
30 """
31 Raise this when a test is expected to fail.
32
33 This is an implementation detail.
34 """
35
36 def __init__(self, exc_info):
37 super(_ExpectedFailure, self).__init__()
38 self.exc_info = exc_info
39
40class _UnexpectedSuccess(Exception):
41 """
42 The test was supposed to fail, but it didn't!
43 """
Michael Foordb3468f72010-12-19 03:19:47 +000044
45
46class _Outcome(object):
47 def __init__(self):
48 self.success = True
49 self.skipped = None
50 self.unexpectedSuccess = None
51 self.expectedFailure = None
52 self.errors = []
53 self.failures = []
54
Benjamin Petersonbed7d042009-07-19 21:01:52 +000055
56def _id(obj):
57 return obj
58
59def skip(reason):
60 """
61 Unconditionally skip a test.
62 """
63 def decorator(test_item):
Benjamin Peterson847a4112010-03-14 15:04:17 +000064 if not (isinstance(test_item, type) and issubclass(test_item, TestCase)):
65 @functools.wraps(test_item)
66 def skip_wrapper(*args, **kwargs):
67 raise SkipTest(reason)
68 test_item = skip_wrapper
69
70 test_item.__unittest_skip__ = True
71 test_item.__unittest_skip_why__ = reason
72 return test_item
Benjamin Petersonbed7d042009-07-19 21:01:52 +000073 return decorator
74
75def skipIf(condition, reason):
76 """
77 Skip a test if the condition is true.
78 """
79 if condition:
80 return skip(reason)
81 return _id
82
83def skipUnless(condition, reason):
84 """
85 Skip a test unless the condition is true.
86 """
87 if not condition:
88 return skip(reason)
89 return _id
90
91
92def expectedFailure(func):
93 @functools.wraps(func)
94 def wrapper(*args, **kwargs):
95 try:
96 func(*args, **kwargs)
97 except Exception:
98 raise _ExpectedFailure(sys.exc_info())
99 raise _UnexpectedSuccess
100 return wrapper
101
102
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000103class _AssertRaisesBaseContext(object):
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000104
105 def __init__(self, expected, test_case, callable_obj=None,
Ezio Melottib4dc2502011-05-06 15:01:41 +0300106 expected_regex=None):
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000107 self.expected = expected
Ezio Melottib4dc2502011-05-06 15:01:41 +0300108 self.test_case = test_case
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000109 if callable_obj is not None:
110 try:
111 self.obj_name = callable_obj.__name__
112 except AttributeError:
113 self.obj_name = str(callable_obj)
114 else:
115 self.obj_name = None
Ezio Melottied3a7d22010-12-01 02:32:32 +0000116 if isinstance(expected_regex, (bytes, str)):
117 expected_regex = re.compile(expected_regex)
118 self.expected_regex = expected_regex
Ezio Melottib4dc2502011-05-06 15:01:41 +0300119 self.msg = None
120
121 def _raiseFailure(self, standardMsg):
122 msg = self.test_case._formatMessage(self.msg, standardMsg)
123 raise self.test_case.failureException(msg)
124
125 def handle(self, name, callable_obj, args, kwargs):
126 """
127 If callable_obj is None, assertRaises/Warns is being used as a
128 context manager, so check for a 'msg' kwarg and return self.
129 If callable_obj is not None, call it passing args and kwargs.
130 """
131 if callable_obj is None:
132 self.msg = kwargs.pop('msg', None)
133 return self
134 with self:
135 callable_obj(*args, **kwargs)
136
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000137
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000138
139class _AssertRaisesContext(_AssertRaisesBaseContext):
140 """A context manager used to implement TestCase.assertRaises* methods."""
141
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000142 def __enter__(self):
Ezio Melotti49008232010-02-08 21:57:48 +0000143 return self
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000144
145 def __exit__(self, exc_type, exc_value, tb):
146 if exc_type is None:
147 try:
148 exc_name = self.expected.__name__
149 except AttributeError:
150 exc_name = str(self.expected)
151 if self.obj_name:
Ezio Melottib4dc2502011-05-06 15:01:41 +0300152 self._raiseFailure("{} not raised by {}".format(exc_name,
153 self.obj_name))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000154 else:
Ezio Melottib4dc2502011-05-06 15:01:41 +0300155 self._raiseFailure("{} not raised".format(exc_name))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000156 if not issubclass(exc_type, self.expected):
157 # let unexpected exceptions pass through
158 return False
Ezio Melotti49008232010-02-08 21:57:48 +0000159 # store exception, without traceback, for later retrieval
160 self.exception = exc_value.with_traceback(None)
Ezio Melottied3a7d22010-12-01 02:32:32 +0000161 if self.expected_regex is None:
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000162 return True
163
Ezio Melottied3a7d22010-12-01 02:32:32 +0000164 expected_regex = self.expected_regex
165 if not expected_regex.search(str(exc_value)):
Ezio Melottib4dc2502011-05-06 15:01:41 +0300166 self._raiseFailure('"{}" does not match "{}"'.format(
167 expected_regex.pattern, str(exc_value)))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000168 return True
169
170
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000171class _AssertWarnsContext(_AssertRaisesBaseContext):
172 """A context manager used to implement TestCase.assertWarns* methods."""
173
174 def __enter__(self):
175 # The __warningregistry__'s need to be in a pristine state for tests
176 # to work properly.
177 for v in sys.modules.values():
178 if getattr(v, '__warningregistry__', None):
179 v.__warningregistry__ = {}
180 self.warnings_manager = warnings.catch_warnings(record=True)
181 self.warnings = self.warnings_manager.__enter__()
182 warnings.simplefilter("always", self.expected)
183 return self
184
185 def __exit__(self, exc_type, exc_value, tb):
186 self.warnings_manager.__exit__(exc_type, exc_value, tb)
187 if exc_type is not None:
188 # let unexpected exceptions pass through
189 return
190 try:
191 exc_name = self.expected.__name__
192 except AttributeError:
193 exc_name = str(self.expected)
194 first_matching = None
195 for m in self.warnings:
196 w = m.message
197 if not isinstance(w, self.expected):
198 continue
199 if first_matching is None:
200 first_matching = w
Ezio Melottied3a7d22010-12-01 02:32:32 +0000201 if (self.expected_regex is not None and
202 not self.expected_regex.search(str(w))):
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000203 continue
204 # store warning for later retrieval
205 self.warning = w
206 self.filename = m.filename
207 self.lineno = m.lineno
208 return
209 # Now we simply try to choose a helpful failure message
210 if first_matching is not None:
Ezio Melottib4dc2502011-05-06 15:01:41 +0300211 self._raiseFailure('"{}" does not match "{}"'.format(
212 self.expected_regex.pattern, str(first_matching)))
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000213 if self.obj_name:
Ezio Melottib4dc2502011-05-06 15:01:41 +0300214 self._raiseFailure("{} not triggered by {}".format(exc_name,
215 self.obj_name))
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000216 else:
Ezio Melottib4dc2502011-05-06 15:01:41 +0300217 self._raiseFailure("{} not triggered".format(exc_name))
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000218
219
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000220class TestCase(object):
221 """A class whose instances are single test cases.
222
223 By default, the test code itself should be placed in a method named
224 'runTest'.
225
226 If the fixture may be used for many test cases, create as
227 many test methods as are needed. When instantiating such a TestCase
228 subclass, specify in the constructor arguments the name of the test method
229 that the instance is to execute.
230
231 Test authors should subclass TestCase for their own tests. Construction
232 and deconstruction of the test's environment ('fixture') can be
233 implemented by overriding the 'setUp' and 'tearDown' methods respectively.
234
235 If it is necessary to override the __init__ method, the base class
236 __init__ method must always be called. It is important that subclasses
237 should not change the signature of their __init__ method, since instances
238 of the classes are instantiated automatically by parts of the framework
239 in order to be run.
240 """
241
242 # This attribute determines which exception will be raised when
243 # the instance's assertion methods fail; test methods raising this
244 # exception will be deemed to have 'failed' rather than 'errored'
245
246 failureException = AssertionError
247
248 # This attribute determines whether long messages (including repr of
249 # objects used in assert methods) will be printed on failure in *addition*
250 # to any explicit message passed.
251
Michael Foord5074df62010-12-03 00:53:09 +0000252 longMessage = True
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000253
Michael Foordc41d1412010-06-10 16:17:07 +0000254 # This attribute sets the maximum length of a diff in failure messages
Michael Foord085dfd32010-06-05 12:17:02 +0000255 # by assert methods using difflib. It is looked up as an instance attribute
256 # so can be configured by individual tests if required.
Michael Foordd50a6b92010-06-05 23:59:34 +0000257
Michael Foord085dfd32010-06-05 12:17:02 +0000258 maxDiff = 80*8
259
Ezio Melottiedd117f2011-04-27 10:20:38 +0300260 # If a string is longer than _diffThreshold, use normal comparison instead
261 # of difflib. See #11763.
262 _diffThreshold = 2**16
263
Benjamin Peterson847a4112010-03-14 15:04:17 +0000264 # Attribute used by TestSuite for classSetUp
265
266 _classSetupFailed = False
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000267
268 def __init__(self, methodName='runTest'):
269 """Create an instance of the class that will use the named test
270 method when executed. Raises a ValueError if the instance does
271 not have a method with the specified name.
272 """
273 self._testMethodName = methodName
Michael Foordb3468f72010-12-19 03:19:47 +0000274 self._outcomeForDoCleanups = None
Michael Foord32e1d832011-01-03 17:00:11 +0000275 self._testMethodDoc = 'No test'
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000276 try:
277 testMethod = getattr(self, methodName)
278 except AttributeError:
Michael Foord32e1d832011-01-03 17:00:11 +0000279 if methodName != 'runTest':
280 # we allow instantiation with no explicit method name
281 # but not an *incorrect* or missing method name
282 raise ValueError("no such test method in %s: %s" %
283 (self.__class__, methodName))
284 else:
285 self._testMethodDoc = testMethod.__doc__
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000286 self._cleanups = []
287
288 # Map types to custom assertEqual functions that will compare
289 # instances of said type in more detail to generate a more useful
290 # error message.
Benjamin Peterson34b2b262011-07-12 19:21:42 -0500291 self._type_equality_funcs = {}
Michael Foord8ca6d982010-11-20 15:34:26 +0000292 self.addTypeEqualityFunc(dict, 'assertDictEqual')
293 self.addTypeEqualityFunc(list, 'assertListEqual')
294 self.addTypeEqualityFunc(tuple, 'assertTupleEqual')
295 self.addTypeEqualityFunc(set, 'assertSetEqual')
296 self.addTypeEqualityFunc(frozenset, 'assertSetEqual')
297 self.addTypeEqualityFunc(str, 'assertMultiLineEqual')
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000298
299 def addTypeEqualityFunc(self, typeobj, function):
300 """Add a type specific assertEqual style function to compare a type.
301
302 This method is for use by TestCase subclasses that need to register
303 their own type equality functions to provide nicer error messages.
304
305 Args:
306 typeobj: The data type to call this function on when both values
307 are of the same type in assertEqual().
308 function: The callable taking two arguments and an optional
309 msg= argument that raises self.failureException with a
310 useful error message when the two arguments are not equal.
311 """
Benjamin Peterson8f326b22009-12-13 02:10:36 +0000312 self._type_equality_funcs[typeobj] = function
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000313
314 def addCleanup(self, function, *args, **kwargs):
315 """Add a function, with arguments, to be called when the test is
316 completed. Functions added are called on a LIFO basis and are
317 called after tearDown on test failure or success.
318
319 Cleanup items are called even if setUp fails (unlike tearDown)."""
320 self._cleanups.append((function, args, kwargs))
321
322 def setUp(self):
323 "Hook method for setting up the test fixture before exercising it."
324 pass
325
326 def tearDown(self):
327 "Hook method for deconstructing the test fixture after testing it."
328 pass
329
Benjamin Peterson847a4112010-03-14 15:04:17 +0000330 @classmethod
331 def setUpClass(cls):
332 "Hook method for setting up class fixture before running tests in the class."
333
334 @classmethod
335 def tearDownClass(cls):
336 "Hook method for deconstructing the class fixture after running all tests in the class."
337
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000338 def countTestCases(self):
339 return 1
340
341 def defaultTestResult(self):
342 return result.TestResult()
343
344 def shortDescription(self):
Michael Foord34c94622010-02-10 15:51:42 +0000345 """Returns a one-line description of the test, or None if no
346 description has been provided.
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000347
Michael Foord34c94622010-02-10 15:51:42 +0000348 The default implementation of this method returns the first line of
349 the specified test method's docstring.
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000350 """
Michael Foord34c94622010-02-10 15:51:42 +0000351 doc = self._testMethodDoc
352 return doc and doc.split("\n")[0].strip() or None
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000353
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000354
355 def id(self):
Benjamin Peterson847a4112010-03-14 15:04:17 +0000356 return "%s.%s" % (strclass(self.__class__), self._testMethodName)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000357
358 def __eq__(self, other):
359 if type(self) is not type(other):
360 return NotImplemented
361
362 return self._testMethodName == other._testMethodName
363
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000364 def __hash__(self):
365 return hash((type(self), self._testMethodName))
366
367 def __str__(self):
Benjamin Peterson847a4112010-03-14 15:04:17 +0000368 return "%s (%s)" % (self._testMethodName, strclass(self.__class__))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000369
370 def __repr__(self):
371 return "<%s testMethod=%s>" % \
Benjamin Peterson847a4112010-03-14 15:04:17 +0000372 (strclass(self.__class__), self._testMethodName)
373
374 def _addSkip(self, result, reason):
375 addSkip = getattr(result, 'addSkip', None)
376 if addSkip is not None:
377 addSkip(self, reason)
378 else:
379 warnings.warn("TestResult has no addSkip method, skips not reported",
380 RuntimeWarning, 2)
381 result.addSuccess(self)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000382
Michael Foordb3468f72010-12-19 03:19:47 +0000383 def _executeTestPart(self, function, outcome, isTest=False):
384 try:
385 function()
386 except KeyboardInterrupt:
387 raise
388 except SkipTest as e:
389 outcome.success = False
390 outcome.skipped = str(e)
391 except _UnexpectedSuccess:
392 exc_info = sys.exc_info()
393 outcome.success = False
394 if isTest:
395 outcome.unexpectedSuccess = exc_info
396 else:
397 outcome.errors.append(exc_info)
398 except _ExpectedFailure:
399 outcome.success = False
400 exc_info = sys.exc_info()
401 if isTest:
402 outcome.expectedFailure = exc_info
403 else:
404 outcome.errors.append(exc_info)
405 except self.failureException:
406 outcome.success = False
407 outcome.failures.append(sys.exc_info())
408 exc_info = sys.exc_info()
409 except:
410 outcome.success = False
411 outcome.errors.append(sys.exc_info())
412
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000413 def run(self, result=None):
414 orig_result = result
415 if result is None:
416 result = self.defaultTestResult()
417 startTestRun = getattr(result, 'startTestRun', None)
418 if startTestRun is not None:
419 startTestRun()
420
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000421 result.startTest(self)
Benjamin Peterson847a4112010-03-14 15:04:17 +0000422
423 testMethod = getattr(self, self._testMethodName)
424 if (getattr(self.__class__, "__unittest_skip__", False) or
425 getattr(testMethod, "__unittest_skip__", False)):
426 # If the class or method was skipped.
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000427 try:
Benjamin Peterson847a4112010-03-14 15:04:17 +0000428 skip_why = (getattr(self.__class__, '__unittest_skip_why__', '')
429 or getattr(testMethod, '__unittest_skip_why__', ''))
430 self._addSkip(result, skip_why)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000431 finally:
432 result.stopTest(self)
433 return
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000434 try:
Michael Foordb3468f72010-12-19 03:19:47 +0000435 outcome = _Outcome()
436 self._outcomeForDoCleanups = outcome
437
438 self._executeTestPart(self.setUp, outcome)
439 if outcome.success:
440 self._executeTestPart(testMethod, outcome, isTest=True)
441 self._executeTestPart(self.tearDown, outcome)
442
443 self.doCleanups()
444 if outcome.success:
445 result.addSuccess(self)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000446 else:
Michael Foordb3468f72010-12-19 03:19:47 +0000447 if outcome.skipped is not None:
448 self._addSkip(result, outcome.skipped)
449 for exc_info in outcome.errors:
450 result.addError(self, exc_info)
451 for exc_info in outcome.failures:
452 result.addFailure(self, exc_info)
453 if outcome.unexpectedSuccess is not None:
Benjamin Peterson847a4112010-03-14 15:04:17 +0000454 addUnexpectedSuccess = getattr(result, 'addUnexpectedSuccess', None)
455 if addUnexpectedSuccess is not None:
456 addUnexpectedSuccess(self)
457 else:
458 warnings.warn("TestResult has no addUnexpectedSuccess method, reporting as failures",
459 RuntimeWarning)
Michael Foordb3468f72010-12-19 03:19:47 +0000460 result.addFailure(self, outcome.unexpectedSuccess)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000461
Michael Foordb3468f72010-12-19 03:19:47 +0000462 if outcome.expectedFailure is not None:
463 addExpectedFailure = getattr(result, 'addExpectedFailure', None)
464 if addExpectedFailure is not None:
465 addExpectedFailure(self, outcome.expectedFailure)
466 else:
467 warnings.warn("TestResult has no addExpectedFailure method, reporting as passes",
468 RuntimeWarning)
469 result.addSuccess(self)
Michael Foord1341bb02011-03-14 19:01:46 -0400470 return result
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000471 finally:
472 result.stopTest(self)
473 if orig_result is None:
474 stopTestRun = getattr(result, 'stopTestRun', None)
475 if stopTestRun is not None:
476 stopTestRun()
477
478 def doCleanups(self):
479 """Execute all cleanup functions. Normally called for you after
480 tearDown."""
Michael Foordb3468f72010-12-19 03:19:47 +0000481 outcome = self._outcomeForDoCleanups or _Outcome()
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000482 while self._cleanups:
Michael Foordb3468f72010-12-19 03:19:47 +0000483 function, args, kwargs = self._cleanups.pop()
484 part = lambda: function(*args, **kwargs)
485 self._executeTestPart(part, outcome)
486
487 # return this for backwards compatibility
488 # even though we no longer us it internally
489 return outcome.success
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000490
491 def __call__(self, *args, **kwds):
492 return self.run(*args, **kwds)
493
494 def debug(self):
495 """Run the test without collecting errors in a TestResult"""
496 self.setUp()
497 getattr(self, self._testMethodName)()
498 self.tearDown()
Michael Foordb8748742010-06-10 16:16:08 +0000499 while self._cleanups:
500 function, args, kwargs = self._cleanups.pop(-1)
501 function(*args, **kwargs)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000502
503 def skipTest(self, reason):
504 """Skip this test."""
505 raise SkipTest(reason)
506
507 def fail(self, msg=None):
508 """Fail immediately, with the given message."""
509 raise self.failureException(msg)
510
511 def assertFalse(self, expr, msg=None):
Ezio Melotti3044fa72010-12-18 17:31:58 +0000512 """Check that the expression is false."""
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000513 if expr:
Ezio Melotti3044fa72010-12-18 17:31:58 +0000514 msg = self._formatMessage(msg, "%s is not false" % safe_repr(expr))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000515 raise self.failureException(msg)
516
517 def assertTrue(self, expr, msg=None):
Ezio Melotti3044fa72010-12-18 17:31:58 +0000518 """Check that the expression is true."""
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000519 if not expr:
Ezio Melotti3044fa72010-12-18 17:31:58 +0000520 msg = self._formatMessage(msg, "%s is not true" % safe_repr(expr))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000521 raise self.failureException(msg)
522
523 def _formatMessage(self, msg, standardMsg):
524 """Honour the longMessage attribute when generating failure messages.
525 If longMessage is False this means:
526 * Use only an explicit message if it is provided
527 * Otherwise use the standard message for the assert
528
529 If longMessage is True:
530 * Use the standard message
531 * If an explicit message is provided, plus ' : ' and the explicit message
532 """
533 if not self.longMessage:
534 return msg or standardMsg
535 if msg is None:
536 return standardMsg
Benjamin Peterson847a4112010-03-14 15:04:17 +0000537 try:
538 # don't switch to '{}' formatting in Python 2.X
539 # it changes the way unicode input is handled
540 return '%s : %s' % (standardMsg, msg)
541 except UnicodeDecodeError:
542 return '%s : %s' % (safe_repr(standardMsg), safe_repr(msg))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000543
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000544 def assertRaises(self, excClass, callableObj=None, *args, **kwargs):
545 """Fail unless an exception of class excClass is thrown
546 by callableObj when invoked with arguments args and keyword
547 arguments kwargs. If a different type of exception is
548 thrown, it will not be caught, and the test case will be
549 deemed to have suffered an error, exactly as for an
550 unexpected exception.
551
552 If called with callableObj omitted or None, will return a
553 context object used like this::
554
Michael Foord1c42b122010-02-05 22:58:21 +0000555 with self.assertRaises(SomeException):
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000556 do_something()
Michael Foord1c42b122010-02-05 22:58:21 +0000557
Ezio Melottib4dc2502011-05-06 15:01:41 +0300558 An optional keyword argument 'msg' can be provided when assertRaises
559 is used as a context object.
560
Michael Foord1c42b122010-02-05 22:58:21 +0000561 The context manager keeps a reference to the exception as
Ezio Melotti49008232010-02-08 21:57:48 +0000562 the 'exception' attribute. This allows you to inspect the
Michael Foord1c42b122010-02-05 22:58:21 +0000563 exception after the assertion::
564
565 with self.assertRaises(SomeException) as cm:
566 do_something()
Ezio Melotti49008232010-02-08 21:57:48 +0000567 the_exception = cm.exception
Michael Foordb57ac6d2010-02-05 23:26:29 +0000568 self.assertEqual(the_exception.error_code, 3)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000569 """
570 context = _AssertRaisesContext(excClass, self, callableObj)
Ezio Melottib4dc2502011-05-06 15:01:41 +0300571 return context.handle('assertRaises', callableObj, args, kwargs)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000572
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000573 def assertWarns(self, expected_warning, callable_obj=None, *args, **kwargs):
574 """Fail unless a warning of class warnClass is triggered
Ezio Melottib4dc2502011-05-06 15:01:41 +0300575 by callable_obj when invoked with arguments args and keyword
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000576 arguments kwargs. If a different type of warning is
577 triggered, it will not be handled: depending on the other
578 warning filtering rules in effect, it might be silenced, printed
579 out, or raised as an exception.
580
Ezio Melottib4dc2502011-05-06 15:01:41 +0300581 If called with callable_obj omitted or None, will return a
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000582 context object used like this::
583
584 with self.assertWarns(SomeWarning):
585 do_something()
586
Ezio Melottib4dc2502011-05-06 15:01:41 +0300587 An optional keyword argument 'msg' can be provided when assertWarns
588 is used as a context object.
589
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000590 The context manager keeps a reference to the first matching
591 warning as the 'warning' attribute; similarly, the 'filename'
592 and 'lineno' attributes give you information about the line
593 of Python code from which the warning was triggered.
594 This allows you to inspect the warning after the assertion::
595
596 with self.assertWarns(SomeWarning) as cm:
597 do_something()
598 the_warning = cm.warning
599 self.assertEqual(the_warning.some_attribute, 147)
600 """
601 context = _AssertWarnsContext(expected_warning, self, callable_obj)
Ezio Melottib4dc2502011-05-06 15:01:41 +0300602 return context.handle('assertWarns', callable_obj, args, kwargs)
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +0000603
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000604 def _getAssertEqualityFunc(self, first, second):
605 """Get a detailed comparison function for the types of the two args.
606
607 Returns: A callable accepting (first, second, msg=None) that will
608 raise a failure exception if first != second with a useful human
609 readable error message for those types.
610 """
611 #
612 # NOTE(gregory.p.smith): I considered isinstance(first, type(second))
613 # and vice versa. I opted for the conservative approach in case
614 # subclasses are not intended to be compared in detail to their super
615 # class instances using a type equality func. This means testing
616 # subtypes won't automagically use the detailed comparison. Callers
617 # should use their type specific assertSpamEqual method to compare
618 # subclasses if the detailed comparison is desired and appropriate.
619 # See the discussion in http://bugs.python.org/issue2578.
620 #
621 if type(first) is type(second):
622 asserter = self._type_equality_funcs.get(type(first))
623 if asserter is not None:
Benjamin Peterson34b2b262011-07-12 19:21:42 -0500624 if isinstance(asserter, str):
625 asserter = getattr(self, asserter)
Benjamin Peterson8f326b22009-12-13 02:10:36 +0000626 return asserter
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000627
628 return self._baseAssertEqual
629
630 def _baseAssertEqual(self, first, second, msg=None):
631 """The default assertEqual implementation, not type specific."""
632 if not first == second:
Benjamin Peterson847a4112010-03-14 15:04:17 +0000633 standardMsg = '%s != %s' % (safe_repr(first), safe_repr(second))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000634 msg = self._formatMessage(msg, standardMsg)
635 raise self.failureException(msg)
636
637 def assertEqual(self, first, second, msg=None):
638 """Fail if the two objects are unequal as determined by the '=='
639 operator.
640 """
641 assertion_func = self._getAssertEqualityFunc(first, second)
642 assertion_func(first, second, msg=msg)
643
644 def assertNotEqual(self, first, second, msg=None):
645 """Fail if the two objects are equal as determined by the '=='
646 operator.
647 """
648 if not first != second:
Benjamin Peterson847a4112010-03-14 15:04:17 +0000649 msg = self._formatMessage(msg, '%s == %s' % (safe_repr(first),
650 safe_repr(second)))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000651 raise self.failureException(msg)
652
Michael Foord321d0592010-11-02 13:44:51 +0000653 def assertAlmostEqual(self, first, second, places=None, msg=None,
Benjamin Petersonb48af542010-04-11 20:43:16 +0000654 delta=None):
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000655 """Fail if the two objects are unequal as determined by their
656 difference rounded to the given number of decimal places
Benjamin Petersonb48af542010-04-11 20:43:16 +0000657 (default 7) and comparing to zero, or by comparing that the
658 between the two objects is more than the given delta.
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000659
660 Note that decimal places (from zero) are usually not the same
661 as significant digits (measured from the most signficant digit).
Benjamin Peterson4ac9ce42009-10-04 14:49:41 +0000662
663 If the two objects compare equal then they will automatically
664 compare almost equal.
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000665 """
Benjamin Peterson4ac9ce42009-10-04 14:49:41 +0000666 if first == second:
Benjamin Petersonb48af542010-04-11 20:43:16 +0000667 # shortcut
Benjamin Peterson4ac9ce42009-10-04 14:49:41 +0000668 return
Benjamin Petersonb48af542010-04-11 20:43:16 +0000669 if delta is not None and places is not None:
670 raise TypeError("specify delta or places not both")
671
672 if delta is not None:
673 if abs(first - second) <= delta:
674 return
675
676 standardMsg = '%s != %s within %s delta' % (safe_repr(first),
677 safe_repr(second),
678 safe_repr(delta))
679 else:
680 if places is None:
681 places = 7
682
683 if round(abs(second-first), places) == 0:
684 return
685
Benjamin Peterson847a4112010-03-14 15:04:17 +0000686 standardMsg = '%s != %s within %r places' % (safe_repr(first),
687 safe_repr(second),
688 places)
Benjamin Petersonb48af542010-04-11 20:43:16 +0000689 msg = self._formatMessage(msg, standardMsg)
690 raise self.failureException(msg)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000691
Michael Foord321d0592010-11-02 13:44:51 +0000692 def assertNotAlmostEqual(self, first, second, places=None, msg=None,
Benjamin Petersonb48af542010-04-11 20:43:16 +0000693 delta=None):
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000694 """Fail if the two objects are equal as determined by their
695 difference rounded to the given number of decimal places
Benjamin Petersonb48af542010-04-11 20:43:16 +0000696 (default 7) and comparing to zero, or by comparing that the
697 between the two objects is less than the given delta.
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000698
699 Note that decimal places (from zero) are usually not the same
700 as significant digits (measured from the most signficant digit).
Benjamin Peterson4ac9ce42009-10-04 14:49:41 +0000701
702 Objects that are equal automatically fail.
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000703 """
Benjamin Petersonb48af542010-04-11 20:43:16 +0000704 if delta is not None and places is not None:
705 raise TypeError("specify delta or places not both")
706 if delta is not None:
707 if not (first == second) and abs(first - second) > delta:
708 return
709 standardMsg = '%s == %s within %s delta' % (safe_repr(first),
710 safe_repr(second),
711 safe_repr(delta))
712 else:
713 if places is None:
714 places = 7
715 if not (first == second) and round(abs(second-first), places) != 0:
716 return
Benjamin Peterson847a4112010-03-14 15:04:17 +0000717 standardMsg = '%s == %s within %r places' % (safe_repr(first),
Benjamin Petersonb48af542010-04-11 20:43:16 +0000718 safe_repr(second),
719 places)
720
721 msg = self._formatMessage(msg, standardMsg)
722 raise self.failureException(msg)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000723
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000724
Michael Foord085dfd32010-06-05 12:17:02 +0000725 def assertSequenceEqual(self, seq1, seq2, msg=None, seq_type=None):
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000726 """An equality assertion for ordered sequences (like lists and tuples).
727
R. David Murrayad13f222010-01-29 22:17:58 +0000728 For the purposes of this function, a valid ordered sequence type is one
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000729 which can be indexed, has a length, and has an equality operator.
730
731 Args:
732 seq1: The first sequence to compare.
733 seq2: The second sequence to compare.
734 seq_type: The expected datatype of the sequences, or None if no
735 datatype should be enforced.
736 msg: Optional message to use on failure instead of a list of
737 differences.
738 """
739 if seq_type != None:
740 seq_type_name = seq_type.__name__
741 if not isinstance(seq1, seq_type):
Benjamin Peterson847a4112010-03-14 15:04:17 +0000742 raise self.failureException('First sequence is not a %s: %s'
743 % (seq_type_name, safe_repr(seq1)))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000744 if not isinstance(seq2, seq_type):
Benjamin Peterson847a4112010-03-14 15:04:17 +0000745 raise self.failureException('Second sequence is not a %s: %s'
746 % (seq_type_name, safe_repr(seq2)))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000747 else:
748 seq_type_name = "sequence"
749
750 differing = None
751 try:
752 len1 = len(seq1)
753 except (TypeError, NotImplementedError):
754 differing = 'First %s has no length. Non-sequence?' % (
755 seq_type_name)
756
757 if differing is None:
758 try:
759 len2 = len(seq2)
760 except (TypeError, NotImplementedError):
761 differing = 'Second %s has no length. Non-sequence?' % (
762 seq_type_name)
763
764 if differing is None:
765 if seq1 == seq2:
766 return
767
Benjamin Peterson847a4112010-03-14 15:04:17 +0000768 seq1_repr = safe_repr(seq1)
769 seq2_repr = safe_repr(seq2)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000770 if len(seq1_repr) > 30:
771 seq1_repr = seq1_repr[:30] + '...'
772 if len(seq2_repr) > 30:
773 seq2_repr = seq2_repr[:30] + '...'
774 elements = (seq_type_name.capitalize(), seq1_repr, seq2_repr)
775 differing = '%ss differ: %s != %s\n' % elements
776
777 for i in range(min(len1, len2)):
778 try:
779 item1 = seq1[i]
780 except (TypeError, IndexError, NotImplementedError):
781 differing += ('\nUnable to index element %d of first %s\n' %
782 (i, seq_type_name))
783 break
784
785 try:
786 item2 = seq2[i]
787 except (TypeError, IndexError, NotImplementedError):
788 differing += ('\nUnable to index element %d of second %s\n' %
789 (i, seq_type_name))
790 break
791
792 if item1 != item2:
793 differing += ('\nFirst differing element %d:\n%s\n%s\n' %
794 (i, item1, item2))
795 break
796 else:
797 if (len1 == len2 and seq_type is None and
798 type(seq1) != type(seq2)):
799 # The sequences are the same, but have differing types.
800 return
801
802 if len1 > len2:
803 differing += ('\nFirst %s contains %d additional '
804 'elements.\n' % (seq_type_name, len1 - len2))
805 try:
806 differing += ('First extra element %d:\n%s\n' %
807 (len2, seq1[len2]))
808 except (TypeError, IndexError, NotImplementedError):
809 differing += ('Unable to index element %d '
810 'of first %s\n' % (len2, seq_type_name))
811 elif len1 < len2:
812 differing += ('\nSecond %s contains %d additional '
813 'elements.\n' % (seq_type_name, len2 - len1))
814 try:
815 differing += ('First extra element %d:\n%s\n' %
816 (len1, seq2[len1]))
817 except (TypeError, IndexError, NotImplementedError):
818 differing += ('Unable to index element %d '
819 'of second %s\n' % (len1, seq_type_name))
Michael Foord2034d9a2010-06-05 11:27:52 +0000820 standardMsg = differing
821 diffMsg = '\n' + '\n'.join(
Benjamin Peterson6e8c7572009-10-04 20:19:21 +0000822 difflib.ndiff(pprint.pformat(seq1).splitlines(),
823 pprint.pformat(seq2).splitlines()))
Michael Foord085dfd32010-06-05 12:17:02 +0000824
825 standardMsg = self._truncateMessage(standardMsg, diffMsg)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000826 msg = self._formatMessage(msg, standardMsg)
827 self.fail(msg)
828
Michael Foord085dfd32010-06-05 12:17:02 +0000829 def _truncateMessage(self, message, diff):
830 max_diff = self.maxDiff
831 if max_diff is None or len(diff) <= max_diff:
832 return message + diff
Michael Foord9dad32e2010-06-05 13:49:56 +0000833 return message + (DIFF_OMITTED % len(diff))
Michael Foord085dfd32010-06-05 12:17:02 +0000834
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000835 def assertListEqual(self, list1, list2, msg=None):
836 """A list-specific equality assertion.
837
838 Args:
839 list1: The first list to compare.
840 list2: The second list to compare.
841 msg: Optional message to use on failure instead of a list of
842 differences.
843
844 """
845 self.assertSequenceEqual(list1, list2, msg, seq_type=list)
846
847 def assertTupleEqual(self, tuple1, tuple2, msg=None):
848 """A tuple-specific equality assertion.
849
850 Args:
851 tuple1: The first tuple to compare.
852 tuple2: The second tuple to compare.
853 msg: Optional message to use on failure instead of a list of
854 differences.
855 """
856 self.assertSequenceEqual(tuple1, tuple2, msg, seq_type=tuple)
857
858 def assertSetEqual(self, set1, set2, msg=None):
859 """A set-specific equality assertion.
860
861 Args:
862 set1: The first set to compare.
863 set2: The second set to compare.
864 msg: Optional message to use on failure instead of a list of
865 differences.
866
Michael Foord91c9da32010-03-20 17:21:27 +0000867 assertSetEqual uses ducktyping to support different types of sets, and
868 is optimized for sets specifically (parameters must support a
869 difference method).
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000870 """
871 try:
872 difference1 = set1.difference(set2)
873 except TypeError as e:
874 self.fail('invalid type when attempting set difference: %s' % e)
875 except AttributeError as e:
876 self.fail('first argument does not support set difference: %s' % e)
877
878 try:
879 difference2 = set2.difference(set1)
880 except TypeError as e:
881 self.fail('invalid type when attempting set difference: %s' % e)
882 except AttributeError as e:
883 self.fail('second argument does not support set difference: %s' % e)
884
885 if not (difference1 or difference2):
886 return
887
888 lines = []
889 if difference1:
890 lines.append('Items in the first set but not the second:')
891 for item in difference1:
892 lines.append(repr(item))
893 if difference2:
894 lines.append('Items in the second set but not the first:')
895 for item in difference2:
896 lines.append(repr(item))
897
898 standardMsg = '\n'.join(lines)
899 self.fail(self._formatMessage(msg, standardMsg))
900
901 def assertIn(self, member, container, msg=None):
902 """Just like self.assertTrue(a in b), but with a nicer default message."""
903 if member not in container:
Benjamin Peterson847a4112010-03-14 15:04:17 +0000904 standardMsg = '%s not found in %s' % (safe_repr(member),
905 safe_repr(container))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000906 self.fail(self._formatMessage(msg, standardMsg))
907
908 def assertNotIn(self, member, container, msg=None):
909 """Just like self.assertTrue(a not in b), but with a nicer default message."""
910 if member in container:
Benjamin Peterson847a4112010-03-14 15:04:17 +0000911 standardMsg = '%s unexpectedly found in %s' % (safe_repr(member),
912 safe_repr(container))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000913 self.fail(self._formatMessage(msg, standardMsg))
914
915 def assertIs(self, expr1, expr2, msg=None):
916 """Just like self.assertTrue(a is b), but with a nicer default message."""
917 if expr1 is not expr2:
Benjamin Peterson847a4112010-03-14 15:04:17 +0000918 standardMsg = '%s is not %s' % (safe_repr(expr1),
919 safe_repr(expr2))
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000920 self.fail(self._formatMessage(msg, standardMsg))
921
922 def assertIsNot(self, expr1, expr2, msg=None):
923 """Just like self.assertTrue(a is not b), but with a nicer default message."""
924 if expr1 is expr2:
Benjamin Peterson847a4112010-03-14 15:04:17 +0000925 standardMsg = 'unexpectedly identical: %s' % (safe_repr(expr1),)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000926 self.fail(self._formatMessage(msg, standardMsg))
927
928 def assertDictEqual(self, d1, d2, msg=None):
Ezio Melottib3aedd42010-11-20 19:04:17 +0000929 self.assertIsInstance(d1, dict, 'First argument is not a dictionary')
930 self.assertIsInstance(d2, dict, 'Second argument is not a dictionary')
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000931
932 if d1 != d2:
Michael Foordcb11b252010-06-05 13:14:43 +0000933 standardMsg = '%s != %s' % (safe_repr(d1, True), safe_repr(d2, True))
Michael Foord085dfd32010-06-05 12:17:02 +0000934 diff = ('\n' + '\n'.join(difflib.ndiff(
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000935 pprint.pformat(d1).splitlines(),
936 pprint.pformat(d2).splitlines())))
Michael Foordcb11b252010-06-05 13:14:43 +0000937 standardMsg = self._truncateMessage(standardMsg, diff)
Benjamin Petersonbed7d042009-07-19 21:01:52 +0000938 self.fail(self._formatMessage(msg, standardMsg))
939
Ezio Melotti0f535012011-04-03 18:02:13 +0300940 def assertDictContainsSubset(self, subset, dictionary, msg=None):
941 """Checks whether dictionary is a superset of subset."""
942 warnings.warn('assertDictContainsSubset is deprecated',
943 DeprecationWarning)
944 missing = []
945 mismatched = []
946 for key, value in subset.items():
947 if key not in dictionary:
948 missing.append(key)
949 elif value != dictionary[key]:
950 mismatched.append('%s, expected: %s, actual: %s' %
951 (safe_repr(key), safe_repr(value),
952 safe_repr(dictionary[key])))
953
954 if not (missing or mismatched):
955 return
956
957 standardMsg = ''
958 if missing:
959 standardMsg = 'Missing: %s' % ','.join(safe_repr(m) for m in
960 missing)
961 if mismatched:
962 if standardMsg:
963 standardMsg += '; '
964 standardMsg += 'Mismatched values: %s' % ','.join(mismatched)
965
966 self.fail(self._formatMessage(msg, standardMsg))
967
968
Raymond Hettinger57bd00a2010-12-24 21:51:48 +0000969 def assertCountEqual(self, first, second, msg=None):
970 """An unordered sequence comparison asserting that the same elements,
971 regardless of order. If the same element occurs more than once,
972 it verifies that the elements occur the same number of times.
Michael Foord8442a602010-03-20 16:58:04 +0000973
Raymond Hettinger57bd00a2010-12-24 21:51:48 +0000974 self.assertEqual(Counter(list(first)),
975 Counter(list(second)))
Michael Foord8442a602010-03-20 16:58:04 +0000976
Raymond Hettinger57bd00a2010-12-24 21:51:48 +0000977 Example:
Michael Foord8442a602010-03-20 16:58:04 +0000978 - [0, 1, 1] and [1, 0, 1] compare equal.
979 - [0, 0, 1] and [0, 1] compare unequal.
Raymond Hettinger57bd00a2010-12-24 21:51:48 +0000980
Michael Foord8442a602010-03-20 16:58:04 +0000981 """
Michael Foorde180d392011-01-28 19:51:48 +0000982 first_seq, second_seq = list(first), list(second)
Michael Foord8442a602010-03-20 16:58:04 +0000983 try:
Michael Foorde180d392011-01-28 19:51:48 +0000984 first = collections.Counter(first_seq)
985 second = collections.Counter(second_seq)
Michael Foord8442a602010-03-20 16:58:04 +0000986 except TypeError:
Raymond Hettinger6518f5e2010-12-24 00:52:54 +0000987 # Handle case with unhashable elements
Michael Foorde180d392011-01-28 19:51:48 +0000988 differences = _count_diff_all_purpose(first_seq, second_seq)
Michael Foord8442a602010-03-20 16:58:04 +0000989 else:
Michael Foorde180d392011-01-28 19:51:48 +0000990 if first == second:
Raymond Hettinger6e165b32010-11-27 09:31:37 +0000991 return
Michael Foorde180d392011-01-28 19:51:48 +0000992 differences = _count_diff_hashable(first_seq, second_seq)
Michael Foord8442a602010-03-20 16:58:04 +0000993
Raymond Hettinger93e233d2010-12-24 10:02:22 +0000994 if differences:
995 standardMsg = 'Element counts were not equal:\n'
Raymond Hettinger57bd00a2010-12-24 21:51:48 +0000996 lines = ['First has %d, Second has %d: %r' % diff for diff in differences]
Raymond Hettinger93e233d2010-12-24 10:02:22 +0000997 diffMsg = '\n'.join(lines)
998 standardMsg = self._truncateMessage(standardMsg, diffMsg)
999 msg = self._formatMessage(msg, standardMsg)
1000 self.fail(msg)
Michael Foord8442a602010-03-20 16:58:04 +00001001
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001002 def assertMultiLineEqual(self, first, second, msg=None):
1003 """Assert that two multi-line strings are equal."""
Ezio Melottib3aedd42010-11-20 19:04:17 +00001004 self.assertIsInstance(first, str, 'First argument is not a string')
1005 self.assertIsInstance(second, str, 'Second argument is not a string')
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001006
1007 if first != second:
Ezio Melottiedd117f2011-04-27 10:20:38 +03001008 # don't use difflib if the strings are too long
1009 if (len(first) > self._diffThreshold or
1010 len(second) > self._diffThreshold):
1011 self._baseAssertEqual(first, second, msg)
Ezio Melottid8b509b2011-09-28 17:37:55 +03001012 firstlines = first.splitlines(keepends=True)
1013 secondlines = second.splitlines(keepends=True)
Michael Foordc653ce32010-07-10 13:52:22 +00001014 if len(firstlines) == 1 and first.strip('\r\n') == first:
1015 firstlines = [first + '\n']
1016 secondlines = [second + '\n']
1017 standardMsg = '%s != %s' % (safe_repr(first, True),
1018 safe_repr(second, True))
1019 diff = '\n' + ''.join(difflib.ndiff(firstlines, secondlines))
Michael Foordcb11b252010-06-05 13:14:43 +00001020 standardMsg = self._truncateMessage(standardMsg, diff)
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001021 self.fail(self._formatMessage(msg, standardMsg))
1022
1023 def assertLess(self, a, b, msg=None):
1024 """Just like self.assertTrue(a < b), but with a nicer default message."""
1025 if not a < b:
Benjamin Peterson847a4112010-03-14 15:04:17 +00001026 standardMsg = '%s not less than %s' % (safe_repr(a), safe_repr(b))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001027 self.fail(self._formatMessage(msg, standardMsg))
1028
1029 def assertLessEqual(self, a, b, msg=None):
1030 """Just like self.assertTrue(a <= b), but with a nicer default message."""
1031 if not a <= b:
Benjamin Peterson847a4112010-03-14 15:04:17 +00001032 standardMsg = '%s not less than or equal to %s' % (safe_repr(a), safe_repr(b))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001033 self.fail(self._formatMessage(msg, standardMsg))
1034
1035 def assertGreater(self, a, b, msg=None):
1036 """Just like self.assertTrue(a > b), but with a nicer default message."""
1037 if not a > b:
Benjamin Peterson847a4112010-03-14 15:04:17 +00001038 standardMsg = '%s not greater than %s' % (safe_repr(a), safe_repr(b))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001039 self.fail(self._formatMessage(msg, standardMsg))
1040
1041 def assertGreaterEqual(self, a, b, msg=None):
1042 """Just like self.assertTrue(a >= b), but with a nicer default message."""
1043 if not a >= b:
Benjamin Peterson847a4112010-03-14 15:04:17 +00001044 standardMsg = '%s not greater than or equal to %s' % (safe_repr(a), safe_repr(b))
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001045 self.fail(self._formatMessage(msg, standardMsg))
1046
1047 def assertIsNone(self, obj, msg=None):
1048 """Same as self.assertTrue(obj is None), with a nicer default message."""
1049 if obj is not None:
Benjamin Peterson847a4112010-03-14 15:04:17 +00001050 standardMsg = '%s is not None' % (safe_repr(obj),)
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001051 self.fail(self._formatMessage(msg, standardMsg))
1052
1053 def assertIsNotNone(self, obj, msg=None):
1054 """Included for symmetry with assertIsNone."""
1055 if obj is None:
1056 standardMsg = 'unexpectedly None'
1057 self.fail(self._formatMessage(msg, standardMsg))
1058
Benjamin Peterson6e8c7572009-10-04 20:19:21 +00001059 def assertIsInstance(self, obj, cls, msg=None):
1060 """Same as self.assertTrue(isinstance(obj, cls)), with a nicer
1061 default message."""
1062 if not isinstance(obj, cls):
Benjamin Peterson847a4112010-03-14 15:04:17 +00001063 standardMsg = '%s is not an instance of %r' % (safe_repr(obj), cls)
Benjamin Peterson6e8c7572009-10-04 20:19:21 +00001064 self.fail(self._formatMessage(msg, standardMsg))
1065
1066 def assertNotIsInstance(self, obj, cls, msg=None):
1067 """Included for symmetry with assertIsInstance."""
1068 if isinstance(obj, cls):
Benjamin Peterson847a4112010-03-14 15:04:17 +00001069 standardMsg = '%s is an instance of %r' % (safe_repr(obj), cls)
Benjamin Peterson6e8c7572009-10-04 20:19:21 +00001070 self.fail(self._formatMessage(msg, standardMsg))
1071
Ezio Melottied3a7d22010-12-01 02:32:32 +00001072 def assertRaisesRegex(self, expected_exception, expected_regex,
1073 callable_obj=None, *args, **kwargs):
1074 """Asserts that the message in a raised exception matches a regex.
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001075
1076 Args:
1077 expected_exception: Exception class expected to be raised.
Ezio Melottied3a7d22010-12-01 02:32:32 +00001078 expected_regex: Regex (re pattern object or string) expected
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001079 to be found in error message.
1080 callable_obj: Function to be called.
Ezio Melottib4dc2502011-05-06 15:01:41 +03001081 msg: Optional message used in case of failure. Can only be used
1082 when assertRaisesRegex is used as a context manager.
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001083 args: Extra args.
1084 kwargs: Extra kwargs.
1085 """
1086 context = _AssertRaisesContext(expected_exception, self, callable_obj,
Ezio Melottied3a7d22010-12-01 02:32:32 +00001087 expected_regex)
Ezio Melottib4dc2502011-05-06 15:01:41 +03001088
1089 return context.handle('assertRaisesRegex', callable_obj, args, kwargs)
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001090
Ezio Melottied3a7d22010-12-01 02:32:32 +00001091 def assertWarnsRegex(self, expected_warning, expected_regex,
1092 callable_obj=None, *args, **kwargs):
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +00001093 """Asserts that the message in a triggered warning matches a regexp.
1094 Basic functioning is similar to assertWarns() with the addition
1095 that only warnings whose messages also match the regular expression
1096 are considered successful matches.
1097
1098 Args:
1099 expected_warning: Warning class expected to be triggered.
Ezio Melottied3a7d22010-12-01 02:32:32 +00001100 expected_regex: Regex (re pattern object or string) expected
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +00001101 to be found in error message.
1102 callable_obj: Function to be called.
Ezio Melottib4dc2502011-05-06 15:01:41 +03001103 msg: Optional message used in case of failure. Can only be used
1104 when assertWarnsRegex is used as a context manager.
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +00001105 args: Extra args.
1106 kwargs: Extra kwargs.
1107 """
1108 context = _AssertWarnsContext(expected_warning, self, callable_obj,
Ezio Melottied3a7d22010-12-01 02:32:32 +00001109 expected_regex)
Ezio Melottib4dc2502011-05-06 15:01:41 +03001110 return context.handle('assertWarnsRegex', callable_obj, args, kwargs)
Antoine Pitrou4bc12ef2010-09-06 19:25:46 +00001111
Ezio Melottied3a7d22010-12-01 02:32:32 +00001112 def assertRegex(self, text, expected_regex, msg=None):
Michael Foorde3ef5f12010-05-08 16:46:14 +00001113 """Fail the test unless the text matches the regular expression."""
Ezio Melottied3a7d22010-12-01 02:32:32 +00001114 if isinstance(expected_regex, (str, bytes)):
Gregory P. Smithed16bf42010-12-16 19:23:05 +00001115 assert expected_regex, "expected_regex must not be empty."
Ezio Melottied3a7d22010-12-01 02:32:32 +00001116 expected_regex = re.compile(expected_regex)
1117 if not expected_regex.search(text):
1118 msg = msg or "Regex didn't match"
1119 msg = '%s: %r not found in %r' % (msg, expected_regex.pattern, text)
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001120 raise self.failureException(msg)
1121
Ezio Melotti8f776302010-12-10 02:32:05 +00001122 def assertNotRegex(self, text, unexpected_regex, msg=None):
Michael Foorde3ef5f12010-05-08 16:46:14 +00001123 """Fail the test if the text matches the regular expression."""
Ezio Melottied3a7d22010-12-01 02:32:32 +00001124 if isinstance(unexpected_regex, (str, bytes)):
1125 unexpected_regex = re.compile(unexpected_regex)
1126 match = unexpected_regex.search(text)
Benjamin Petersonb48af542010-04-11 20:43:16 +00001127 if match:
Ezio Melottied3a7d22010-12-01 02:32:32 +00001128 msg = msg or "Regex matched"
Benjamin Petersonb48af542010-04-11 20:43:16 +00001129 msg = '%s: %r matches %r in %r' % (msg,
1130 text[match.start():match.end()],
Ezio Melottied3a7d22010-12-01 02:32:32 +00001131 unexpected_regex.pattern,
Benjamin Petersonb48af542010-04-11 20:43:16 +00001132 text)
1133 raise self.failureException(msg)
1134
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001135
Ezio Melottied3a7d22010-12-01 02:32:32 +00001136 def _deprecate(original_func):
1137 def deprecated_func(*args, **kwargs):
1138 warnings.warn(
1139 'Please use {0} instead.'.format(original_func.__name__),
1140 DeprecationWarning, 2)
1141 return original_func(*args, **kwargs)
1142 return deprecated_func
1143
Ezio Melotti361467e2011-04-03 17:37:58 +03001144 # see #9424
Ezio Melotti0f535012011-04-03 18:02:13 +03001145 failUnlessEqual = assertEquals = _deprecate(assertEqual)
1146 failIfEqual = assertNotEquals = _deprecate(assertNotEqual)
1147 failUnlessAlmostEqual = assertAlmostEquals = _deprecate(assertAlmostEqual)
1148 failIfAlmostEqual = assertNotAlmostEquals = _deprecate(assertNotAlmostEqual)
1149 failUnless = assert_ = _deprecate(assertTrue)
1150 failUnlessRaises = _deprecate(assertRaises)
1151 failIf = _deprecate(assertFalse)
Ezio Melottied3a7d22010-12-01 02:32:32 +00001152 assertRaisesRegexp = _deprecate(assertRaisesRegex)
1153 assertRegexpMatches = _deprecate(assertRegex)
1154
1155
1156
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001157class FunctionTestCase(TestCase):
1158 """A test case that wraps a test function.
1159
1160 This is useful for slipping pre-existing test functions into the
1161 unittest framework. Optionally, set-up and tidy-up functions can be
1162 supplied. As with TestCase, the tidy-up ('tearDown') function will
1163 always be called if the set-up ('setUp') function ran successfully.
1164 """
1165
1166 def __init__(self, testFunc, setUp=None, tearDown=None, description=None):
1167 super(FunctionTestCase, self).__init__()
1168 self._setUpFunc = setUp
1169 self._tearDownFunc = tearDown
1170 self._testFunc = testFunc
1171 self._description = description
1172
1173 def setUp(self):
1174 if self._setUpFunc is not None:
1175 self._setUpFunc()
1176
1177 def tearDown(self):
1178 if self._tearDownFunc is not None:
1179 self._tearDownFunc()
1180
1181 def runTest(self):
1182 self._testFunc()
1183
1184 def id(self):
1185 return self._testFunc.__name__
1186
1187 def __eq__(self, other):
1188 if not isinstance(other, self.__class__):
1189 return NotImplemented
1190
1191 return self._setUpFunc == other._setUpFunc and \
1192 self._tearDownFunc == other._tearDownFunc and \
1193 self._testFunc == other._testFunc and \
1194 self._description == other._description
1195
1196 def __ne__(self, other):
1197 return not self == other
1198
1199 def __hash__(self):
1200 return hash((type(self), self._setUpFunc, self._tearDownFunc,
1201 self._testFunc, self._description))
1202
1203 def __str__(self):
Benjamin Peterson847a4112010-03-14 15:04:17 +00001204 return "%s (%s)" % (strclass(self.__class__),
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001205 self._testFunc.__name__)
1206
1207 def __repr__(self):
Benjamin Peterson847a4112010-03-14 15:04:17 +00001208 return "<%s tec=%s>" % (strclass(self.__class__),
Benjamin Petersonbed7d042009-07-19 21:01:52 +00001209 self._testFunc)
1210
1211 def shortDescription(self):
1212 if self._description is not None:
1213 return self._description
1214 doc = self._testFunc.__doc__
1215 return doc and doc.split("\n")[0].strip() or None