I'm looking for a way to have the following behavior with argparse.
Imagine as an example that I want a program that pretty print a file given as input. And I also want an optional argument to display the list of file types that the program handles. What I'd like is the following behavior.
myparser ./myfile.json
> this would pretty print the file myfile.json
myparser --list
> this would display the list of handled file types
However, I don't see how to do it: in the second line, argparse asks me to provide the filepath
argument.
So I could either do what I want by doing myparser . --list
and code the program such that the filepath
argument is ignored when the list argument is provided.
Or I could set the filepath
argument as optional, which would require me to do the following:
myparser --filepath ./myfile.json
Both solutions work fine, but I'm still curious about if it is possible to have the behavior that I want. Do you have any solution ? (Remark that the behavior that I'm looking for is exactly the one of the help
argument)
First, just for contrast, you need to make the file name optional. That means providing an explicit --print
option instead of a required file name, so that your usage is either
myparser --print ./myfile.json
or
myparser --list
Closer to what you actually want is to define a custom action that exits your script early, much like version
or help
.
class ListAction(argparse.Action):
def __init__(self, option_strings, dest=argparse.SUPPRESS, default=argparse.SUPPRESS, help=None):
super().__init__(option_strings=option_strings, nargs=0, dest=dest, default=default, help=help)
def __call__(self, parser, namespace, values, option_string=None):
print("Hello world")
parser.exit()
p = argparse.ArgumentParser()
p.add_argument('name')
p.add_argument('--list', action=ListAction)
Now myparser --list
will process --list
and exit before it notices that the required filename option is missing.
(The definition of ListAction
is modeled explicitly after the definition of argparse._HelpAction
.)