Bug report
Bug description:
In Python 3.13 onwards:
from contextlib import ExitStack from unittest import mock with mock.patch("__main__.open", mock.mock_open()) as m: with ExitStack() as exit_stack: with exit_stack.enter_context(open("/tmp/test.txt", "w")): pass
raises
TypeError: mock_open.<locals>._exit_side_effect() takes 3 positional arguments but 4 were given
The issue seems to come from 3f7c081
It appears that in Python versions 3.12 and earlier, mock_open().__exit__ was always called with 4 args (self, exctype, excinst, exctb) when used with contextlib.ExitStack but that used to be a no-op before the exit handler was added.
I'm not sure whether this should be fixed by:
- changing the way
ExitStackcalls its stack of__exit__callbacks - making
mock_openandopenmore similar, or - making
mock_open's exit handler take*args, **kwargssame as the enter handler??
Thanks
CPython versions tested on:
3.12, 3.13, 3.14
Operating systems tested on:
Linux
Linked PRs
- gh-150484: Fix mock_open __exit__ with contextlib.ExitStack #150521
- fix unittest.mock: make mock_open.__exit__ accept variable args (gh-150484) #150535
- [3.14] gh-150484: Fix mock_open __exit__ with contextlib.ExitStack #151829
- [3.13] gh-150484: Fix mock_open __exit__ with contextlib.ExitStack (GH-151829) #151861