Sorry, something went wrong.
|
This would gradually nudge the code toward the way it should have been designed from the outset. Eventually, it might save someone a few minutes of time. That said, this is a pretty minor issue (ignoring unused arguments). Changing the behavior will be inconvenient for people who happened to have fed in an unused argument in code that is currently functioning correctly — we've breaking code that was sloppy but correct — I'm not sure they will appreciate being forced to make a minor edit that doesn't change behavior or fix any problem that they have. |
Sorry, something went wrong.
|
@rhettinger thank you for your input. However, I don't quite agree with some of your points. Changing the behavior will be inconvenient for people who happened to have fed in an unused argument in code that is currently functioning correctly Two things here:
>>> from argparse import *
>>> parser = ArgumentParser()
>>> parser.add_argument('--foo', action=BooleanOptionalAction, type=int) # we expect `int`
>>> parser.parse_args(['--foo']) # but get `bool`
Namespace(foo=True)
Here's the code does not "function correctly" in a sense that type is ignored. While user explicitly asks to use int. The second example: >>> from argparse import *
>>> parser = ArgumentParser()
>>> parser.add_argument('--foo', action=BooleanOptionalAction, choices=['on', 'off'])
>>> parser.parse_args(['--foo'])
Namespace(foo=True)
And again: user specifies two values that must be respected. But, they are ignored. We also do not document this behaviour: So, any user might expect it to work similarly to other action types. Which is not the case right now. All in all, I see this as an improvement:
|
Sorry, something went wrong.
|
Let's merge this before the beta if there's no remaining objections. |
Sorry, something went wrong.
|
Hi from the future (post 2025 Q4 when the params were removed). For the record, there was a reason those parameters were accepted in the first place and that reason seems totally unexamined here. Also the codesearch described missed the mark quite a bit (for example, as of 3-Feb-2026):
And this change is documented in the wrong place -- people don't instantiate argparse.BooleanOptionalAction directly (which is proven in the docs for that class: https://docs.python.org/3.14/library/argparse.html#argparse.BooleanOptionalAction), instead they call add_argument with the action param set accordingly, but https://docs.python.org/3.14/library/argparse.html#choices shows nothing about choices=None (for example) suddenly being a fatal error. You might want to do something like action=BooleanOptionalAction, choices=var_that_evaluates_to_none when you're calling add_argument dynamically. There are workarounds of course, but this breakage seems unforced - when we could have just warned about questionable code without changing the API: if type is not None:
warnings._whatever("type is implied when action is BooleanOptionalAction")
if choices is not None:
warnings._whatever("choices are predefined with BooleanOptionalAction")
if metavar is not None:
warnings._whatever("there is no metavar when action is BooleanOptionalAction")
|
Sorry, something went wrong.
argparse.BooleanOptionalAction was added in 3.9
#85039 removed just a single wrong parameter.
But, it was on time when 3.9 was recently released, and no deprecation warning was issued.
The parameter was just removed.
But, since we already have 3.9, 3.10, and 3.11, (and all alphas of 3.12), I am sure that we need a deprecation period now.
People might use this (the use-case is probably wrong), but I don't like breaking things for no clear benefit.
I'm feeling pretty safe about this deprecation (I even considered just removing these parameters straight away), because code search shows that no one is using these arguments: https://cs.github.com/?q=action%3DBooleanOptionalAction
Plus, they don't make any sense and are mostly not changing any behaviour of BooleanOptionalAction.
CC @barneygale since you've asked for this 😆
CC @rhettinger and @hauntsaninja since you've reviewed #85039