From 72f66b0e6f179812ab54bd83216773c222593158 Mon Sep 17 00:00:00 2001 From: John Mason Date: Tue, 22 Oct 2019 10:26:44 -0400 Subject: [PATCH] Raise an error if mocker is used in a `with` context Ref: #164 --- src/pytest_mock/plugin.py | 14 ++++++++++++++ tests/test_pytest_mock.py | 19 +++++++++++++++++++ 2 files changed, 33 insertions(+) diff --git a/src/pytest_mock/plugin.py b/src/pytest_mock/plugin.py index 6311696..fcf8ec3 100644 --- a/src/pytest_mock/plugin.py +++ b/src/pytest_mock/plugin.py @@ -156,8 +156,22 @@ def _start_patch(self, mock_func, *args, **kwargs): 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] + frame = caller[0] + info = inspect.getframeinfo(frame) + code_context = " ".join(info.code_context).strip() + + if "with mocker" in code_context: + raise ValueError( + "Using mocker in a with context is not supported. " + "https://github.com/pytest-dev/pytest-mock#note-about-usage-as-context-manager" + ) + def multiple(self, *args, **kwargs): """API to mock.patch.multiple""" return self._start_patch(self.mock_module.patch.multiple, *args, **kwargs) diff --git a/tests/test_pytest_mock.py b/tests/test_pytest_mock.py index 865f7bd..4ff741a 100644 --- a/tests/test_pytest_mock.py +++ b/tests/test_pytest_mock.py @@ -721,3 +721,22 @@ def test_get_random_number(mocker): result = testdir.runpytest_subprocess() result.stdout.fnmatch_lines("* 1 passed in *") assert "RuntimeError" not in result.stderr.str() + + +def test_abort_context_manager(mocker): + class A(object): + def doIt(self): + return False + + a = A() + + with pytest.raises(ValueError) as excinfo: + with mocker.patch.object(a, "doIt", return_value=True): + assert a.doIt() == True + + 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