cpython icon indicating copy to clipboard operation
cpython copied to clipboard

BooleanOptionalAction does not correctly resolve arguments that are defined as starting with "--no-"

Open noah-gil opened this issue 1 year ago • 6 comments

Bug report

Bug description:

When using argparse to define a BooleanOptionAction that starts with "--no-", it is not possible to set the flag as True. This is counterintuitive, as one would expect that passing the argument should set the flag to True, regardless of the name of the argument.

The bug appears to originate from this line of code:

setattr(namespace, self.dest, not option_string.startswith('--no-'))

Because BooleanOptionAction always generates another argument that starts with "--no-", the code here attempts to check for the case where the user passed in that generated argument. It doesn't consider the possibility that the original argument could also start with "--no-".

This code here demonstrates the bug:

import argparse
parser = argparse.ArgumentParser()
parser.add_argument('--no-foo', action=argparse.BooleanOptionalAction)
assert(parser.parse_args(['--no-no-foo']).no_foo == False) # Passes
assert(parser.parse_args(['--no-foo']).no_foo == True) # Fails

While I tested this on 3.10, the argparse snippet above is from the main branch, which suggests the bug is in the latest version.

CPython versions tested on:

3.10

Operating systems tested on:

Linux

Linked PRs

  • gh-118103
  • gh-125894

noah-gil avatar Apr 16 '24 18:04 noah-gil

I think the proper thing to do here is to deprecate adding boolean options that start with --no-. They certainly do not work as intended.

encukou avatar Apr 22 '24 12:04 encukou

I concur with @encukou. We can even reject them without a deprecation period if they are absolutely broken.

serhiy-storchaka avatar Apr 23 '24 16:04 serhiy-storchaka

I don't think they're absolutely broken. Someone might be relying on the current behaviour (accidentally, most likely).

encukou avatar Apr 24 '24 09:04 encukou

@encukou, are you interesting in creating a patch for deprecating a BooleanOptionAction that starts with "--no-"?

serhiy-storchaka avatar Sep 23 '24 17:09 serhiy-storchaka

It's on my TODO list, but it doesn't have much priority. Feel free to do it.

encukou avatar Sep 23 '24 21:09 encukou

I do not see much value in deprecation, so I can only create a PR for disallowing such names.

serhiy-storchaka avatar Sep 24 '24 02:09 serhiy-storchaka