Skip to content

Commit

Permalink
Raise error if any version of patch is used as a context manager (#168)
Browse files Browse the repository at this point in the history
Raise error if any version of patch is used as a context manager
  • Loading branch information
nicoddemus committed Nov 18, 2019
2 parents ed8216b + d3d10a5 commit 845876e
Show file tree
Hide file tree
Showing 2 changed files with 20 additions and 7 deletions.
12 changes: 6 additions & 6 deletions src/pytest_mock/plugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -147,21 +147,17 @@ def _start_patch(self, mock_func, *args, **kwargs):
module, registering the patch to stop it later and returns the
mock object resulting from the mock call.
"""
self._enforce_no_with_context(inspect.stack())
p = mock_func(*args, **kwargs)
mocked = p.start()
self._patches.append(p)
if hasattr(mocked, "reset_mock"):
self._mocks.append(mocked)
return mocked

def object(self, *args, **kwargs):
"""API to mock.patch.object"""
self._enforce_no_with_context(inspect.stack())
return self._start_patch(self.mock_module.patch.object, *args, **kwargs)

def _enforce_no_with_context(self, stack):
"""raises a ValueError if mocker is used in a with context"""
caller = stack[1]
caller = stack[2]
frame = caller[0]
info = inspect.getframeinfo(frame)
code_context = " ".join(info.code_context).strip()
Expand All @@ -172,6 +168,10 @@ def _enforce_no_with_context(self, stack):
"https://github.com/pytest-dev/pytest-mock#note-about-usage-as-context-manager"
)

def object(self, *args, **kwargs):
"""API to mock.patch.object"""
return self._start_patch(self.mock_module.patch.object, *args, **kwargs)

def multiple(self, *args, **kwargs):
"""API to mock.patch.multiple"""
return self._start_patch(self.mock_module.patch.multiple, *args, **kwargs)
Expand Down
15 changes: 14 additions & 1 deletion tests/test_pytest_mock.py
Original file line number Diff line number Diff line change
Expand Up @@ -723,7 +723,7 @@ def test_get_random_number(mocker):
assert "RuntimeError" not in result.stderr.str()


def test_abort_context_manager(mocker):
def test_abort_patch_object_context_manager(mocker):
class A(object):
def doIt(self):
return False
Expand All @@ -740,3 +740,16 @@ def doIt(self):
)

assert str(excinfo.value) == expected_error_msg


def test_abort_patch_context_manager(mocker):
with pytest.raises(ValueError) as excinfo:
with mocker.patch("some_package"):
pass

expected_error_msg = (
"Using mocker in a with context is not supported. "
"https://github.com/pytest-dev/pytest-mock#note-about-usage-as-context-manager"
)

assert str(excinfo.value) == expected_error_msg

0 comments on commit 845876e

Please sign in to comment.