Skip to content

mock.patch with autospec does not consume self / cls argument #76273

Open

Description

@bclau
mannequin
BPO 32092
Nosy @cjw296, @voidspace, @phmc, @lisroach, @mariocj89, @BCLAU, @tirkarthi
PRs
  • gh-76273: Consume self when autospeccing unbound instance methods #4476
  • Note: these values reflect the state of the issue at the time it was migrated and might not reflect the current state.

    Show more details

    GitHub fields:

    assignee = None
    closed_at = None
    created_at = <Date 2017-11-20.15:50:21.285>
    labels = ['3.7', '3.8', 'type-bug', 'library', '3.9']
    title = 'mock.patch with autospec does not consume self / cls argument'
    updated_at = <Date 2019-10-28.20:46:16.247>
    user = 'https://github.com/bclau'

    bugs.python.org fields:

    activity = <Date 2019-10-28.20:46:16.247>
    actor = 'pconnell'
    assignee = 'none'
    closed = False
    closed_date = None
    closer = None
    components = ['Library (Lib)']
    creation = <Date 2017-11-20.15:50:21.285>
    creator = 'cbelu'
    dependencies = []
    files = []
    hgrepos = []
    issue_num = 32092
    keywords = ['patch']
    message_count = 2.0
    messages = ['306559', '306560']
    nosy_count = 7.0
    nosy_names = ['cjw296', 'michael.foord', 'pconnell', 'lisroach', 'mariocj89', 'cbelu', 'xtreak']
    pr_nums = ['4476']
    priority = 'normal'
    resolution = None
    stage = 'patch review'
    status = 'open'
    superseder = None
    type = 'behavior'
    url = 'https://bugs.python.org/issue32092'
    versions = ['Python 3.7', 'Python 3.8', 'Python 3.9']

    Linked PRs

    Activity

    1. bclau commented on Nov 20, 2017

      bclaumannequin
      MannequinAuthor

      Currently, the autospec=True argument can be passed to mock.patch, but when trying to make assertions on the call and its arguments, it can fail, as it expects an instance / class instance reference as the first argument (self / cls arguments are not consumed when autospec-ing).

      Steps to reproduce:

      >>> import mock
      >>> from mock.tests import testmock
      >>>
      >>> with mock.patch.object(testmock.Something, 'meth', autospec=True):
      ...     smth = testmock.Something()
      ...     smth.meth(mock.sentinel.a, mock.sentinel.b, mock.sentinel.c, mock.sentinel.d)
      ...     smth.meth.assert_called_once_with(mock.sentinel.a, mock.sentinel.b, mock.sentinel.c, mock.sentinel.d)
      ...
      <MagicMock name='meth()' id='139792133225424'>
      Traceback (most recent call last):
        File "<stdin>", line 4, in <module>
        File "/usr/local/lib/python2.7/dist-packages/mock/mock.py", line 318, in assert_called_once_with
          return mock.assert_called_once_with(*args, **kwargs)
        File "/usr/local/lib/python2.7/dist-packages/mock/mock.py", line 948, in assert_called_once_with
          return self.assert_called_with(*args, **kwargs)
        File "/usr/local/lib/python2.7/dist-packages/mock/mock.py", line 937, in assert_called_with
          six.raise_from(AssertionError(_error_message(cause)), cause)
        File "/usr/local/lib/python2.7/dist-packages/six.py", line 718, in raise_from
          raise value
      AssertionError: Expected call: meth(sentinel.a, sentinel.b, sentinel.c, sentinel.d)
      Actual call: meth(<mock.tests.testmock.Something object at 0x7f23e456dcd0>, sentinel.a, sentinel.b, sentinel.c, sentinel.d)

      Expected result: no AssertionError.

    2. added
      type-bugAn unexpected behavior, bug, or error
      stdlibStandard Library Python modules in the Lib/ directory
      on Nov 20, 2017
    3. bclau commented on Nov 20, 2017

      bclaumannequin
      MannequinAuthor

      Currently, the autospec=True argument can be passed to mock.patch, but when trying to make assertions on the call and its arguments, it can fail, as it expects an instance / class instance reference as the first argument (self / cls arguments are not consumed when autospec-ing).

      Steps to reproduce:

      ubuntu@ubuntu:/opt/stack/cpython$ ./python
      Python 3.7.0a2+ (heads/mock-add-autospec:51a9270, Nov 20 2017, 06:48:44)
      [GCC 5.4.0 20160609] on linux
      Type "help", "copyright", "credits" or "license" for more information.
      >>> from unittest import mock
      from unittest.test.testmock import testmock
      with mock.patch.object(testmock.Something, 'meth', autospec=True):
          smth = testmock.Something()
          smth.meth(mock.sentinel.a, mock.sentinel.b, mock.sentinel.c, mock.sentinel.d)
          smth.meth.assert_called_once_with(mock.sentinel.a, mock.sentinel.b, mock.sentinel.c, mock.sentinel.d)
      >>> >>> >>> ... ... ... ... <MagicMock name='meth()' id='140281858112024'>
      Traceback (most recent call last):
        File "<stdin>", line 4, in <module>
        File "/opt/stack/cpython/Lib/unittest/mock.py", line 196, in assert_called_once_with
          return mock.assert_called_once_with(*args, **kwargs)
        File "/opt/stack/cpython/Lib/unittest/mock.py", line 856, in assert_called_once_with
          return self.assert_called_with(*args, **kwargs)
        File "/opt/stack/cpython/Lib/unittest/mock.py", line 845, in assert_called_with
          raise AssertionError(_error_message()) from cause
      AssertionError: Expected call: meth(sentinel.a, sentinel.b, sentinel.c, sentinel.d)
      Actual call: meth(<unittest.test.testmock.testmock.Something object at 0x7f95ea529a80>, sentinel.a, sentinel.b, sentinel.c, sentinel.d)

      Expected result: no AssertionError.

    4. transferred this issue fromon Apr 10, 2022
    5. iritkatriel commented on Oct 30, 2022

      @iritkatriel
      Member

      @BCLAU is this still relevant? The code changed quite a lot since 3.7.

    6. added
      pendingThe issue will be closed if no feedback is provided
      on Oct 30, 2022
    7. stephenfin commented on Dec 17, 2025

      @stephenfin

      @iritkatriel I don't have the ability to reopen this bug, but this is still relevant. Using the same reproducer, albeit with unittest.mock instead of mock.

      from unittest import mock
      
      class Something(object):
          def meth(self, a, b, c, d=None): pass
      
          @classmethod
          def cmeth(cls, a, b, c, d=None): pass
      
          @staticmethod
          def smeth(a, b, c, d=None): pass
      
      with mock.patch.object(Something, 'meth', autospec=True):
          smth = Something()
          smth.meth(mock.sentinel.a, mock.sentinel.b, mock.sentinel.c, mock.sentinel.d)
          smth.meth.assert_called_once_with(mock.sentinel.a, mock.sentinel.b, mock.sentinel.c, mock.sentinel.d

      Running this with the most recent Python:

      python3.14 test.py
      Traceback (most recent call last):
        File "/tmp/bar/test.py", line 15, in <module>
          smth.meth.assert_called_once_with(mock.sentinel.a, mock.sentinel.b, mock.sentinel.c, mock.sentinel.d)
          ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
        File "/usr/lib64/python3.14/unittest/mock.py", line 245, in assert_called_once_with
          return mock.assert_called_once_with(*args, **kwargs)
                 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~^^^^^^^^^^^^^^^^^
        File "/usr/lib64/python3.14/unittest/mock.py", line 997, in assert_called_once_with
          return self.assert_called_with(*args, **kwargs)
                 ~~~~~~~~~~~~~~~~~~~~~~~^^^^^^^^^^^^^^^^^
        File "/usr/lib64/python3.14/unittest/mock.py", line 985, in assert_called_with
          raise AssertionError(_error_message()) from cause
      AssertionError: expected call not found.
      Expected: meth(sentinel.a, sentinel.b, sentinel.c, sentinel.d)
        Actual: meth(<__main__.Something object at 0x7f30ac1c96a0>, sentinel.a, sentinel.b, sentinel.c, sentinel.d)

      We have been carrying a fix for this in https://github.com/openstack/oslotest/ for a long time here. I suspect an upstream solution would look very similar.

    8. added 2 commits that reference this issue on Mar 27, 2026
    9. self-assigned this
      on Mar 27, 2026
    10. johnslavik commented on Mar 27, 2026

      @johnslavik
      Member

      Worth checking if this relates to GH-71902.

    11. removed
      pendingThe issue will be closed if no feedback is provided
      on Mar 28, 2026
    Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

    Metadata

    Metadata

    Assignees

    Labels

    stdlibStandard Library Python modules in the Lib/ directorytype-bugAn unexpected behavior, bug, or error

    Projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions