Skip to content

Commit 101ff35

Browse files
Issue #24336: The contextmanager decorator now works with functions with
keyword arguments called "func" and "self". Patch by Martin Panter.
1 parent acac1e0 commit 101ff35

File tree

4 files changed

+17
-6
lines changed

4 files changed

+17
-6
lines changed

Lib/contextlib.py

+3-3
Original file line numberDiff line numberDiff line change
@@ -34,7 +34,7 @@ def inner(*args, **kwds):
3434
class _GeneratorContextManager(ContextDecorator):
3535
"""Helper for @contextmanager decorator."""
3636

37-
def __init__(self, func, *args, **kwds):
37+
def __init__(self, func, args, kwds):
3838
self.gen = func(*args, **kwds)
3939
self.func, self.args, self.kwds = func, args, kwds
4040
# Issue 19330: ensure context manager instances have good docstrings
@@ -52,7 +52,7 @@ def _recreate_cm(self):
5252
# _GCM instances are one-shot context managers, so the
5353
# CM must be recreated each time a decorated function is
5454
# called
55-
return self.__class__(self.func, *self.args, **self.kwds)
55+
return self.__class__(self.func, self.args, self.kwds)
5656

5757
def __enter__(self):
5858
try:
@@ -123,7 +123,7 @@ def some_generator(<arguments>):
123123
"""
124124
@wraps(func)
125125
def helper(*args, **kwds):
126-
return _GeneratorContextManager(func, *args, **kwds)
126+
return _GeneratorContextManager(func, args, kwds)
127127
return helper
128128

129129

Lib/test/test_contextlib.py

+8
Original file line numberDiff line numberDiff line change
@@ -111,6 +111,14 @@ def test_instance_docstring_given_cm_docstring(self):
111111
baz = self._create_contextmanager_attribs()(None)
112112
self.assertEqual(baz.__doc__, "Whee!")
113113

114+
def test_keywords(self):
115+
# Ensure no keyword arguments are inhibited
116+
@contextmanager
117+
def woohoo(self, func, args, kwds):
118+
yield (self, func, args, kwds)
119+
with woohoo(self=11, func=22, args=33, kwds=44) as target:
120+
self.assertEqual(target, (11, 22, 33, 44))
121+
114122

115123
class ClosingTestCase(unittest.TestCase):
116124

Lib/test/test_with.py

+3-3
Original file line numberDiff line numberDiff line change
@@ -12,8 +12,8 @@
1212

1313

1414
class MockContextManager(_GeneratorContextManager):
15-
def __init__(self, func, *args, **kwds):
16-
super().__init__(func, *args, **kwds)
15+
def __init__(self, *args):
16+
super().__init__(*args)
1717
self.enter_called = False
1818
self.exit_called = False
1919
self.exit_args = None
@@ -31,7 +31,7 @@ def __exit__(self, type, value, traceback):
3131

3232
def mock_contextmanager(func):
3333
def helper(*args, **kwds):
34-
return MockContextManager(func, *args, **kwds)
34+
return MockContextManager(func, args, kwds)
3535
return helper
3636

3737

Misc/NEWS

+3
Original file line numberDiff line numberDiff line change
@@ -60,6 +60,9 @@ Core and Builtins
6060
Library
6161
-------
6262

63+
- Issue #24336: The contextmanager decorator now works with functions with
64+
keyword arguments called "func" and "self". Patch by Martin Panter.
65+
6366
- Issue #24489: ensure a previously set C errno doesn't disturb cmath.polar().
6467

6568
- Issue #5633: Fixed timeit when the statement is a string and the setup is not.

0 commit comments

Comments
 (0)