86 votes

Comment faire en sorte que les arguments de groupe python argparse s'excluent mutuellement sans préfixe?

Python2.7 argparse n'accepte que les arguments facultatifs (préfixés) dans des groupes mutuellement exclusifs :

 parser = argparse.ArgumentParser(prog='mydaemon')
action = parser.add_mutually_exclusive_group(required=True)
action.add_argument('--start', action='store_true', help='Starts %(prog)s daemon')
action.add_argument('--stop', action='store_true', help='Stops %(prog)s daemon')
action.add_argument('--restart', action='store_true', help='Restarts %(prog)s daemon')

$ mydaemon -h

 usage: mydaemon [-h] (--start | --stop | --restart)

optional arguments:
  -h, --help  show this help message and exit
  --start     Starts mydaemon daemon
  --stop      Stops mydaemon daemon
  --restart   Restarts mydaemon daemon

Existe-t-il un moyen de faire en sorte que les arguments argparse se comportent comme le contrôle traditionnel du démon Unix :

 (start | stop | restart) and not (--start | --stop | --restart) ?

95voto

madjardi Points 475

de pymotw

 import argparse

parser = argparse.ArgumentParser()

group = parser.add_mutually_exclusive_group()
group.add_argument('-a', action='store_true')
group.add_argument('-b', action='store_true')

print parser.parse_args()

sortir:

 $ python argparse_mutually_exclusive.py -h  
usage: argparse_mutually_exclusive.py [-h] [-a | -b]

optional arguments:  
  -h, --help  show this help message and exit  
  -a  
  -b  

$ python argparse_mutually_exclusive.py -a  
Namespace(a=True, b=False)

$ python argparse_mutually_exclusive.py -b  
Namespace(a=False, b=True)

$ python argparse_mutually_exclusive.py -a -b  
usage: argparse_mutually_exclusive.py [-h] [-a | -b]  
argparse_mutually_exclusive.py: error: argument -b: not allowed with argument -a

version 2

 import argparse

parser = argparse.ArgumentParser()

subparsers = parser.add_subparsers(help='commands')

# A list command
list_parser = subparsers.add_parser('list', help='List contents')
list_parser.add_argument('dirname', action='store', help='Directory to list')

# A create command
create_parser = subparsers.add_parser('create', help='Create a directory')
create_parser.add_argument('dirname', action='store', help='New directory to create')
create_parser.add_argument('--read-only', default=False, action='store_true',
                       help='Set permissions to prevent writing to the directory',
                       )

# A delete command
delete_parser = subparsers.add_parser('delete', help='Remove a directory')
delete_parser.add_argument('dirname', action='store', help='The directory to remove')
delete_parser.add_argument('--recursive', '-r', default=False, action='store_true',
                       help='Remove the contents of the directory, too',
                       )

print parser.parse_args(['list', 'a s d', ])
>>> Namespace(dirname='a s d')
print parser.parse_args(['list', 'a s d', 'create' ])
>>> error: unrecognized arguments: create

43voto

Adam Wagner Points 7232

Il semble que vous vouliez un argument positionnel au lieu d'options mutuellement exclusives. Vous pouvez utiliser « choix » pour restreindre les options acceptables possibles.

 parser = ArgumentParser()
parser.add_argument('action', choices=('start', 'stop', 'restart'))

Cela produit une ligne d'utilisation qui ressemble à ceci :

 usage: foo.py [-h] {start,stop,restart}

13voto

Craig Points 95

S'appuyant sur la réponse d'Adam... si vous vouliez spécifier une valeur par défaut, vous pouvez toujours faire ce qui suit afin qu'ils puissent effectivement la laisser vide.

 import argparse

ActionHelp = """
    Start = Starts the daemon (default)
    Stop = Stops the daemon
    Restart = Restarts the daemon
    """
parser = argparse.ArgumentParser(formatter_class=argparse.RawTextHelpFormatter)

parser.add_argument('action', nargs = '?', choices=('start', 'stop', 'restart'),
    default = 'start', help = ActionHelp)

print parser.parse_args(''.split())
print
print parser.parse_args('-h'.split())

qui imprimera :

 Namespace(action='start')

usage: program.py [-h] [{start,stop,restart}]

postional arguments:
    {start,stop,restart}
                      Start = Starts the daemon (default)
                      Stop = Stops the daemon
                      Restart = Restarts the daemon

optional arguments:
    -h, --help        show this help message and exit

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X