Skip to content

gh-78416: Add the "%" format unit for required keyword-only arguments - #155329

Draft
serhiy-storchaka wants to merge 1 commit into
python:mainfrom
serhiy-storchaka:getargs-required-kwonly
Draft

gh-78416: Add the "%" format unit for required keyword-only arguments#155329
serhiy-storchaka wants to merge 1 commit into
python:mainfrom
serhiy-storchaka:getargs-required-kwonly

Conversation

@serhiy-storchaka

@serhiy-storchaka serhiy-storchaka commented Aug 7, 2026

Copy link
Copy Markdown
Member

PyArg_ParseTupleAndKeywords() supports only three of the four kinds of parameters: keyword-only arguments are either all required ("OO$OO") or all optional ("O|O$O"), so f(a, b=None, *, c, d=None) cannot be expressed.

This is one of three alternative implementations, made for comparison as suggested in the issue; this one adds a new format unit. % replaces $ and starts the keyword-only arguments as required, | making the rest optional: "O|O%O|O" corresponds to f(a, b=None, *, c, d=None). Its meaning does not depend on whether | was specified before it, so the meaning of every unit is fixed by the text to its left and no lookahead is needed except in the fast-return path.

Argument Clinic uses % when $ cannot express the signature, so such functions can now use the limited C API, and it no longer rejects a required keyword-only parameter after an optional positional one.

The cost is a format character, which can then never be used for anything else, spent on a marker that nearly duplicates $: without a preceding | they are the same thing, "OO%OO" and "OO$OO" both meaning f(a, b, *, c, d). The two diverge only when | precedes the marker, where $ makes the keyword-only arguments optional and % keeps them required until the next |.

The other two alternatives: #155330, #155331.

…eTupleAndKeywords()

The new format unit "%" starts the keyword-only arguments which are
required until "|", so that they can be mixed with optional arguments.
Unlike "$", it does not depend on whether "|" was specified before it.

Argument Clinic uses it if "$" cannot express the signature, so that such
functions can now use the limited C API.  It also no longer rejects
a required keyword-only parameter after an optional positional one.
@read-the-docs-community

Copy link
Copy Markdown

Documentation build overview

📚 cpython-previews | 🛠️ Build #33959883 | 📁 Comparing 1b45059 against main (7c653e2)

  🔍 Preview build  

3 files changed
± c-api/arg.html
± whatsnew/3.16.html
± whatsnew/changelog.html

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant