Ce dont j'ai besoin c'est:
pro [-a xxx | [-b yyy -c zzz]]
J'ai essayé ça mais ça ne marche pas. Est-ce que quelqu'un peut m'aider?
group= parser.add_argument_group('Model 2')
group_ex = group.add_mutually_exclusive_group()
group_ex.add_argument("-a", type=str, action = "store", default = "", help="test")
group_ex_2 = group_ex.add_argument_group("option 2")
group_ex_2.add_argument("-b", type=str, action = "store", default = "", help="test")
group_ex_2.add_argument("-c", type=str, action = "store", default = "", help="test")
Merci!
add_mutually_exclusive_group
ne rend pas un groupe entier mutuellement exclusif. Cela rend les options du groupe mutuellement exclusives.
Ce que vous cherchez, c'est sous-commandes . Au lieu de prog [-a xxxx | [-b yyy -c zzz]], vous auriez:
prog
command 1
-a: ...
command 2
-b: ...
-c: ...
Pour invoquer avec le premier jeu d'arguments:
prog command_1 -a xxxx
Pour invoquer avec le deuxième ensemble d'arguments:
prog command_2 -b yyyy -c zzzz
Vous pouvez également définir les arguments de la sous-commande comme positionnels.
prog command_1 xxxx
Un peu comme git ou svn:
git commit -am
git merge develop
# create the top-level parser
parser = argparse.ArgumentParser(prog='PROG')
parser.add_argument('--foo', action='store_true', help='help for foo arg.')
subparsers = parser.add_subparsers(help='help for subcommand')
# create the parser for the "command_1" command
parser_a = subparsers.add_parser('command_1', help='command_1 help')
parser_a.add_argument('a', type=str, help='help for bar, positional')
# create the parser for the "command_2" command
parser_b = subparsers.add_parser('command_2', help='help for command_2')
parser_b.add_argument('-b', type=str, help='help for b')
parser_b.add_argument('-c', type=str, action='store', default='', help='test')
>>> parser.print_help()
usage: PROG [-h] [--foo] {command_1,command_2} ...
positional arguments:
{command_1,command_2}
help for subcommand
command_1 command_1 help
command_2 help for command_2
optional arguments:
-h, --help show this help message and exit
--foo help for foo arg.
>>>
>>> parser.parse_args(['command_1', 'working'])
Namespace(a='working', foo=False)
>>> parser.parse_args(['command_1', 'wellness', '-b x'])
usage: PROG [-h] [--foo] {command_1,command_2} ...
PROG: error: unrecognized arguments: -b x
Bonne chance.
Bien que réponse de Jonathan convient parfaitement aux options complexes, il existe une solution très simple qui fonctionnera pour les cas simples, par exemple. 1 option exclut 2 autres options comme dans
command [- a xxx | [ -b yyy | -c zzz ]]
ou même comme dans la question initiale:
pro [-a xxx | [-b yyy -c zzz]]
Voici comment je le ferais:
parser = argparse.ArgumentParser()
# group 1
parser.add_argument("-q", "--query", help="query", required=False)
parser.add_argument("-f", "--fields", help="field names", required=False)
# group 2
parser.add_argument("-a", "--aggregation", help="aggregation",
required=False)
J'utilise ici les options données à un wrapper de ligne de commande pour interroger un mongodb. L'instance collection
peut appeler la méthode aggregate
ou la méthode find
avec des arguments facultatifs query
et fields
. Vous voyez donc pourquoi les deux premiers arguments sont compatibles et le dernier ne l'est pas.
Alors maintenant, je lance parser.parse_args()
et vérifie son contenu:
args = parser().parse_args()
print args.aggregation
if args.aggregation and (args.query or args.fields):
print "-a and -q|-f are mutually exclusive ..."
sys.exit(2)
Bien sûr, ce petit bidouillage ne fonctionne que pour des cas simples et il deviendrait un cauchemar de vérifier toutes les options possibles si vous avez plusieurs options et groupes mutuellement exclusifs. Dans ce cas, vous devriez casser vos options pour commander des groupes comme suggéré par Jonathan.
Il existe un correctif python (en développement) qui vous permettrait de le faire.
http://bugs.python.org/issue10984
L'idée est de permettre le chevauchement de groupes mutuellement exclusifs. Donc, usage
pourrait ressembler à:
pro [-a xxx | -b yyy] [-a xxx | -c zzz]
Changer le code argparse afin de pouvoir créer deux groupes comme ceci était la partie facile. Changer le code de formatage usage
a nécessité l'écriture d'un HelpFormatter
personnalisé.
Dans argparse
, les groupes d'actions n'affectent pas l'analyse. Ils ne sont qu'un outil de formatage help
. Dans le help
, les groupes mutuellement exclusifs n'affectent que la ligne usage
. Lors de l'analyse, parser
utilise les groupes mutuellement exclusifs pour construire un dictionnaire des conflits potentiels (a
ne peut pas se produire avec b
ou c
, b
ne peut pas se produire avec a
, etc.), puis génère une erreur en cas de conflit.
Sans ce patch argparse, je pense que votre meilleur choix est de tester l’espace de noms produit par parse_args
vous-même (par exemple, si a
et b
ont des valeurs différentes de la valeur par défaut), et créez votre propre erreur. Vous pouvez même utiliser le mécanisme d'erreur du parseur.
parser.error('custom error message')