This issue tracker has been migrated to GitHub, and is currently read-only.
For more information, see the GitHub FAQs in the Python's Developer Guide.

classification
Title: mock.seal has infinite recursion with int class attributes
Type: crash Stage: resolved
Components: Library (Lib) Versions: Python 3.11, Python 3.10, Python 3.9
process
Status: closed Resolution: fixed
Dependencies: Superseder:
Assigned To: Nosy List: dseomn, iritkatriel, miss-islington, sobolevn, vstinner, xtreak
Priority: normal Keywords: patch

Created on 2021-09-09 22:09 by dseomn, last changed 2022-04-11 14:59 by admin. This issue is now closed.

Pull Requests
URL Status Linked Edit
PR 28300 merged sobolevn, 2021-09-12 21:29
PR 28326 merged miss-islington, 2021-09-14 10:21
PR 28327 merged miss-islington, 2021-09-14 10:21
Messages (8)
msg401525 - (view) Author: David Mandelberg (dseomn) Date: 2021-09-09 22:09
The code below seems to have infinite recursion in the mock.seal call with python 3.9.2.

from unittest import mock
class Foo:
  foo = 0
foo = mock.create_autospec(Foo)
mock.seal(foo)
msg401669 - (view) Author: Irit Katriel (iritkatriel) * (Python committer) Date: 2021-09-12 18:58
Reproduced on 3.11:

>>> foo = mock.create_autospec(Foo)
>>> mock.seal(foo)

^CTraceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "/Users/iritkatriel/src/cpython-1/Lib/unittest/mock.py", line 2917, in seal
    seal(m)
    ^^^^^^^
  File "/Users/iritkatriel/src/cpython-1/Lib/unittest/mock.py", line 2917, in seal
    seal(m)
    ^^^^^^^
  File "/Users/iritkatriel/src/cpython-1/Lib/unittest/mock.py", line 2917, in seal
    seal(m)
    ^^^^^^^
  [Previous line repeated 645 more times]
  File "/Users/iritkatriel/src/cpython-1/Lib/unittest/mock.py", line 2911, in seal
    m = getattr(mock, attr)
        ^^^^^^^^^^^^^^^^^^^
  File "/Users/iritkatriel/src/cpython-1/Lib/unittest/mock.py", line 662, in __getattr__
    result = create_autospec(
             ^^^^^^^^^^^^^^^^
  File "/Users/iritkatriel/src/cpython-1/Lib/unittest/mock.py", line 2672, in create_autospec
    mock = Klass(parent=_parent, _new_parent=_parent, _new_name=_new_name,
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/Users/iritkatriel/src/cpython-1/Lib/unittest/mock.py", line 416, in __new__
    new = type(cls.__name__, bases, {'__doc__': cls.__doc__})
          ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
KeyboardInterrupt
msg401670 - (view) Author: Irit Katriel (iritkatriel) * (Python committer) Date: 2021-09-12 19:03
Pdb) list
2916 	        if m._mock_new_parent is mock:
2917 	          try:
2918 	            seal(m)
2919 	          except:
2920 	            breakpoint()
2921 ->	            raise
2922 	
2923 	
2924 	class _AsyncIterator:
2925 	    """
2926 	    Wraps an iterator in an asynchronous iterator.
(Pdb) p m
<MagicMock name='mock.foo.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.denominator.as_integer_ratio' spec='builtin_function_or_method' id='4405352848'>
msg401694 - (view) Author: Nikita Sobolev (sobolevn) * (Python triager) Date: 2021-09-13 11:01
I've proposed a solution, based on the assumption that we don't need to recurse into `_SpecState` props:

```
if isinstance(m._mock_children.get(attr), _SpecState):
   continue
```

It seems like a simple and reasonable thing to do.
Link: https://github.com/python/cpython/pull/28300
msg401765 - (view) Author: STINNER Victor (vstinner) * (Python committer) Date: 2021-09-14 10:20
New changeset 7f60c9e1c6e22cc0e846a872c318570926cd3094 by Nikita Sobolev in branch 'main':
bpo-45156: Fixes inifite loop on unittest.mock.seal() (GH-28300)
https://github.com/python/cpython/commit/7f60c9e1c6e22cc0e846a872c318570926cd3094
msg401773 - (view) Author: miss-islington (miss-islington) Date: 2021-09-14 10:50
New changeset 13257d9fca13dfa1bda5b802d68ddaec72f3a07e by Miss Islington (bot) in branch '3.9':
bpo-45156: Fixes inifite loop on unittest.mock.seal() (GH-28300)
https://github.com/python/cpython/commit/13257d9fca13dfa1bda5b802d68ddaec72f3a07e
msg401774 - (view) Author: STINNER Victor (vstinner) * (Python committer) Date: 2021-09-14 11:00
New changeset fd74d2680ef96c0140bc02cf94d1cf1f2ef814c2 by Miss Islington (bot) in branch '3.10':
bpo-45156: Fixes inifite loop on unittest.mock.seal() (GH-28300) (GH-28326)
https://github.com/python/cpython/commit/fd74d2680ef96c0140bc02cf94d1cf1f2ef814c2
msg401945 - (view) Author: STINNER Victor (vstinner) * (Python committer) Date: 2021-09-16 13:22
Thanks for the report and the fix!
History
Date User Action Args
2022-04-11 14:59:49adminsetgithub: 89319
2021-09-16 13:22:23vstinnersetstatus: open -> closed
resolution: fixed
messages: + msg401945

stage: patch review -> resolved
2021-09-14 11:00:21vstinnersetmessages: + msg401774
2021-09-14 10:50:31miss-islingtonsetmessages: + msg401773
2021-09-14 10:21:52miss-islingtonsetpull_requests: + pull_request26738
2021-09-14 10:21:09miss-islingtonsetnosy: + miss-islington
pull_requests: + pull_request26737
2021-09-14 10:20:46vstinnersetnosy: + vstinner
messages: + msg401765
2021-09-13 11:01:50sobolevnsetmessages: + msg401694
2021-09-12 21:29:15sobolevnsetkeywords: + patch
nosy: + sobolevn

pull_requests: + pull_request26714
stage: patch review
2021-09-12 19:03:16iritkatrielsetmessages: + msg401670
2021-09-12 18:58:40iritkatrielsetnosy: + iritkatriel

messages: + msg401669
versions: + Python 3.10, Python 3.11
2021-09-12 00:33:15xtreaksetnosy: + xtreak
2021-09-09 22:09:24dseomncreate