mirror of https://github.com/python/cpython
Issue 10242. Switching unittest.TestCase.assertItemsEqual to use a collections.Counter under the hood.
This fixes bugs when comparing collections of items like sets that can be sorted without raising an exception but where sorting has no meaning.
This commit is contained in:
parent
a17f076f61
commit
e6e0e26780
|
@ -1,5 +1,6 @@
|
||||||
"""Test case implementation"""
|
"""Test case implementation"""
|
||||||
|
|
||||||
|
import collections
|
||||||
import sys
|
import sys
|
||||||
import functools
|
import functools
|
||||||
import difflib
|
import difflib
|
||||||
|
@ -850,14 +851,12 @@ class TestCase(object):
|
||||||
self.fail(self._formatMessage(msg, standardMsg))
|
self.fail(self._formatMessage(msg, standardMsg))
|
||||||
|
|
||||||
def assertItemsEqual(self, expected_seq, actual_seq, msg=None):
|
def assertItemsEqual(self, expected_seq, actual_seq, msg=None):
|
||||||
"""An unordered sequence / set specific comparison. It asserts that
|
"""An unordered sequence specific comparison. It asserts that
|
||||||
expected_seq and actual_seq contain the same elements. It is
|
actual_seq and expected_seq have the same element counts.
|
||||||
the equivalent of::
|
Equivalent to::
|
||||||
|
|
||||||
self.assertEqual(sorted(expected_seq), sorted(actual_seq))
|
self.assertEqual(Counter(iter(actual_seq)),
|
||||||
|
Counter(iter(expected_seq)))
|
||||||
Raises with an error message listing which elements of expected_seq
|
|
||||||
are missing from actual_seq and vice versa if any.
|
|
||||||
|
|
||||||
Asserts that each element has the same count in both sequences.
|
Asserts that each element has the same count in both sequences.
|
||||||
Example:
|
Example:
|
||||||
|
@ -872,17 +871,18 @@ class TestCase(object):
|
||||||
"comparing unequal types"]:
|
"comparing unequal types"]:
|
||||||
warnings.filterwarnings("ignore", _msg, DeprecationWarning)
|
warnings.filterwarnings("ignore", _msg, DeprecationWarning)
|
||||||
try:
|
try:
|
||||||
expected = sorted(expected_seq)
|
actual = collections.Counter(iter(actual_seq))
|
||||||
actual = sorted(actual_seq)
|
expected = collections.Counter(iter(expected_seq))
|
||||||
except TypeError:
|
except TypeError:
|
||||||
# Unsortable items (example: set(), complex(), ...)
|
# Unsortable items (example: set(), complex(), ...)
|
||||||
expected = list(expected_seq)
|
|
||||||
actual = list(actual_seq)
|
actual = list(actual_seq)
|
||||||
missing, unexpected = unorderable_list_difference(
|
expected = list(expected_seq)
|
||||||
expected, actual, ignore_duplicate=False
|
missing, unexpected = unorderable_list_difference(expected, actual)
|
||||||
)
|
|
||||||
else:
|
else:
|
||||||
return self.assertSequenceEqual(expected, actual, msg=msg)
|
if actual == expected:
|
||||||
|
return
|
||||||
|
missing = list(expected - actual)
|
||||||
|
unexpected = list(actual - expected)
|
||||||
|
|
||||||
errors = []
|
errors = []
|
||||||
if missing:
|
if missing:
|
||||||
|
|
|
@ -711,6 +711,11 @@ class Test_TestCase(unittest.TestCase, TestEquality, TestHashing):
|
||||||
self.assertRaises(self.failureException, self.assertItemsEqual,
|
self.assertRaises(self.failureException, self.assertItemsEqual,
|
||||||
[1, {'b': 2}, None, True], [{'b': 2}, True, None])
|
[1, {'b': 2}, None, True], [{'b': 2}, True, None])
|
||||||
|
|
||||||
|
# Same elements which don't reliably compare, in
|
||||||
|
# different order, see issue 10242
|
||||||
|
a = [{2,4}, {1,2}]
|
||||||
|
b = a[::-1]
|
||||||
|
self.assertItemsEqual(a, b)
|
||||||
|
|
||||||
def testAssertSetEqual(self):
|
def testAssertSetEqual(self):
|
||||||
set1 = set()
|
set1 = set()
|
||||||
|
|
|
@ -22,6 +22,9 @@ Core and Builtins
|
||||||
Library
|
Library
|
||||||
-------
|
-------
|
||||||
|
|
||||||
|
- Issue #10242: unittest.TestCase.assertItemsEqual makes too many assumgptions
|
||||||
|
about input.
|
||||||
|
|
||||||
- Issue #10611: SystemExit should not cause a unittest test run to exit.
|
- Issue #10611: SystemExit should not cause a unittest test run to exit.
|
||||||
|
|
||||||
- Issue #6791: Limit header line length (to 65535 bytes) in http.client,
|
- Issue #6791: Limit header line length (to 65535 bytes) in http.client,
|
||||||
|
|
Loading…
Reference in New Issue