bpo-36871: Ensure method signature is used when asserting mock calls to a method by tirkarthi · Pull Request #13261 · python/cpython
Though this is an internal method there is a note on the docstring of _call_matcher that it could be a tuple. It's not specified in docs that this could be a tuple. I haven't seen a usecase of it in other projects too. There is a test for this usecase but it's not using autospec so it didn't fail with my PR I guess. Relevant test using tuples
Given a call (or simply an (args, kwargs) tuple), return a
comparison key suitable for matching with other calls.
There could be a below test that passes with checking _call to be a tuple.
def test_assert_has_calls_tuple(self): class Something: def __init__(self): pass def meth(self, a, b, c, d=None): pass m = create_autospec(Something) m.meth(1, 2, 3, 1) m.assert_has_calls([('meth', (1, 2, 3, 1), {})])
On having a strict check of only using _Call it will fail since it will go on to use the constructor signature.
./python.exe -m unittest Lib.unittest.test.testmock.testmock.MockTest.test_assert_has_calls_tuple
F
======================================================================
FAIL: test_assert_has_calls_tuple (Lib.unittest.test.testmock.testmock.MockTest)
----------------------------------------------------------------------
Traceback (most recent call last):
File "/Users/karthikeyansingaravelan/stuff/python/cpython/Lib/unittest/test/testmock/testmock.py", line 1387, in test_assert_has_calls_tuple
m.assert_has_calls([('meth', (1, 2, 3, 1), {})])
File "/Users/karthikeyansingaravelan/stuff/python/cpython/Lib/unittest/mock.py", line 876, in assert_has_calls
raise AssertionError(
AssertionError: Calls not found.
Expected: [('meth', (1, 2, 3, 1), {})]
Actual: [call.meth(1, 2, 3, 1)].
----------------------------------------------------------------------
Ran 1 test in 0.063s
FAILED (failures=1)
I am leaning towards removing tuple to support only _Call since the error message is also not useful. We can perhaps change it in 3.9 to accept only _Call and then revert back if someone complains that it breaks their workflow given there is plenty of time. I am not sure about backporting it to 3.8 though since beta is out. Would also like to know thoughts from @voidspace since this was added in the original commit where mock was added.