SvbZ3r0
SvbZ3r0

Reputation: 638

Optional flag that works by itself or with all other arguments (like -h)

I realize the title might be confusing, but I didn't know how to word my problem.

My program's command line syntax looks like this: conv.py val from to, where to is optional, but I don't think that should matter.

I'm trying to add a flag that forces my program to ignore cached data and update its database. It should work like this:

conv.py -f val from to

but also like this:

conv.py -f

I know it should be possible to do this because the inbuilt -h flag in argparse works in a similar manner where you can say conv.py val from to or conv.py -h or conv.py -h val. However, I am at a loss as to how to achieve this. My current code just has the -f flag as an optional argument:

def parse_args():
    parser = argparse.ArgumentParser(prog='conv')
    parser.add_argument('-f', action='store_true')
    parser.add_argument('value')
    parser.add_argument('from_', metavar='from' )
    parser.add_argument('to', nargs='?', default='neg')
    args = parser.parse_args()
    return args.from_, args.to, args.value, args.f

I would like to make it so the presence of the -f flag is acceptable by itself or with all the other arguments. Any help is appreciated.

Upvotes: 1

Views: 233

Answers (1)

wim
wim

Reputation: 362557

To do that you would create a custom action which exits the parsing:

import argparse

class MyAction(argparse.Action):

    def do_the_thing(self):
        print("hello from my action")

    def __call__(self, parser, namespace, values, option_string=None):
        self.do_the_thing()
        parser.exit()

parser = argparse.ArgumentParser()
parser.add_argument('value')
parser.add_argument('from_', metavar='from' )
parser.add_argument('to', nargs='?', default='neg')
parser.add_argument("-f", nargs=0, action=MyAction)
args = parser.parse_args()
print("after args parsed")

Now if -f was passed, then print("after args parsed") will not be reached regardless of whether required arguments were sent or not. You may access the parser namespace from within the action instance.

Upvotes: 2

Related Questions