Skip to content

Commit 9e9c3c4

Browse files
gh-158320: Reject optional groups with a var-positional parameter in Argument Clinic (GH-158323)
Such a combination is ambiguous: the number of arguments does not tell whether the group is passed or all arguments belong to the var-positional parameter.
1 parent 89eee1f commit 9e9c3c4

3 files changed

Lines changed: 110 additions & 0 deletions

File tree

‎Lib/test/test_clinic.py‎

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2106,6 +2106,28 @@ def test_disallowed_grouping__no_matching_bracket(self):
21062106
err = "Function 'empty_group' has a ']' without a matching '['"
21072107
self.expect_failure(block, err)
21082108

2109+
def test_disallowed_grouping__varpos(self):
2110+
err = "cannot use optional groups with a var-positional parameter"
2111+
block = """
2112+
module foo
2113+
foo.bar
2114+
[
2115+
a: int
2116+
]
2117+
*args: tuple
2118+
"""
2119+
self.expect_failure(block, err, lineno=5)
2120+
block = """
2121+
module foo
2122+
foo.bar
2123+
a: int
2124+
*args: tuple
2125+
[
2126+
b: int
2127+
]
2128+
"""
2129+
self.expect_failure(block, err, lineno=4)
2130+
21092131
def test_disallowed_grouping__must_be_position_only(self):
21102132
dataset = ("""
21112133
with_kwds

‎Tools/clinic/libclinic/dsl_parser.py‎

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1161,6 +1161,12 @@ def bad_node(self, node: ast.AST) -> None:
11611161

11621162
kind: inspect._ParameterKind
11631163
if is_vararg:
1164+
if any(p.group for p in self.function.parameters.values()):
1165+
# With "foo([a, b], *args)" the number of arguments does not
1166+
# tell whether the group is passed or all arguments belong
1167+
# to the var-positional parameter.
1168+
fail(f"Function {self.function.name!r} cannot use optional "
1169+
f"groups with a var-positional parameter.")
11641170
kind = inspect.Parameter.VAR_POSITIONAL
11651171
elif is_var_keyword:
11661172
kind = inspect.Parameter.VAR_KEYWORD
@@ -1303,6 +1309,9 @@ def parse_star(self, function: Function, version: VersionTuple | None) -> None:
13031309

13041310
def parse_opening_square_bracket(self, function: Function) -> None:
13051311
"""Parse opening parameter group symbol '['."""
1312+
if any(p.is_vararg() for p in function.parameters.values()):
1313+
fail(f"Function {function.name!r} cannot use optional groups "
1314+
f"with a var-positional parameter.")
13061315
# A group can only be nested in a group which does not contain
13071316
# parameters yet, but two groups on the same nesting level can
13081317
# follow each other.

‎clinic/test.c.h‎

Lines changed: 79 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

0 commit comments

Comments
 (0)