If have autospec=True, then no ValueError is raised. If autospec=False or not defined, then the ValueError is raised. import sys from unittest import mock def wrapped_func(value): raise ValueError(value) @mock.patch('__main__.wrapped_func', autospec=True, wraps=wrapped_func) def main(mock_wrap): wrapped_func("testing") if '__main__' == __name__: sys.exit(main())
I can reproduce the problem and have analyzed it a bit. My use case is a bit different, I want to use autospec=True and wraps= so that I can mock unbound methods but return the result from the original method (see also https://docs.python.org/3/library/unittest.mock-examples.html#mocking-unbound-methods). The problem in the mock code is that mock.return_value actually calls __get_return_value() which replaces the actual return value mock.DEFAULT (which is stored in self._mock_return_value) with a new child mock. When the mock is then called and _mock_call() is executed, the wrapped function is not executed because self._mock_return_value is not mock.DEFAULT anymore: if (self._mock_wraps is not None and self._mock_return_value is DEFAULT): return self._mock_wraps(*args, **kwargs) if ret_val is DEFAULT: ret_val = self.return_value return ret_val Since self._mock_return_value is not DEFAULT anymore it doesn't matter if the mock wraps something and it will instead just return a new mock. I think that the side effect of the assignment to self.return_value in _setup_func() is not intentional, i.e. the child mock should actually be created only if there is an outside access to return_value, but not when it is just wrapped in a function. The assignment can be made side effect free by assigning the internal attribute _mock_return_value (see attached patch). This solves the problem for me. I've attached a patch that fixes the problem and doesn't seem to introduce a regression (all unittest.mock tests pass). If somebody is interested in getting this merged, I'm happy to provide a regression test and everything else that is needed to get this merged. Cheers, Lukas