2010-12-30 2 views
5

Я использую argparse для обработки cmd args, я хочу, если не указано никаких аргументов, затем распечатайте справочное сообщение, но теперь синтаксический анализ выдает ошибку и затем выйдите. мой код:как разрешить сообщение справки для анализатора, а не ошибку и выйти

def main(): 
    print "in abing/start/main" 
    parser = argparse.ArgumentParser(prog="abing")#, usage="%(prog)s <command> [args] [--help]") 
    parser.add_argument("-v", "--verbose", action="store_true", default=False, help="show verbose output") 

    subparsers = parser.add_subparsers(title="commands") 

    bkr_subparser = subparsers.add_parser("beaker", help="beaker inspection") 
    bkr_subparser.set_defaults(command=beaker_command) 
    bkr_subparser.add_argument("-m", "--max", action="store", default=3, type=int, help="max resubmit count") 
    bkr_subparser.add_argument("-g", "--grain", action="store", default="J", choices=["J", "RS", "R", "T", "job", "recipeset", "recipe", "task"], type=str, help="resubmit selection granularity") 
    bkr_subparser.add_argument("job_ids", nargs=1, action="store", help="list of job id to be monitored") 

    et_subparser = subparsers.add_parser("errata", help="errata inspection") 
    et_subparser.set_defaults(command=errata_command) 
    et_subparser.add_argument("-w", "--workflows", action="store_true", help="generate workflows for the erratum") 
    et_subparser.add_argument("-r", "--run", action="store_true", help="generate workflows, and run for the erratum") 
    et_subparser.add_argument("-s", "--start-monitor", action="store_true", help="start monitor the errata system") 
    et_subparser.add_argument("-d", "--daemon", action="store_true", help="run monitor into daemon mode") 
    et_subparser.add_argument("erratum", action="store", nargs=1, metavar="ERRATUM", help="erratum id") 

    if len(sys.argv) == 1: 
     parser.print_help() 
     return 

    args = parser.parse_args() 
    args.command(args) 

    return 

, как я могу это сделать? спасибо.

+0

* теперь синтаксический разбор выдаст ошибку, а затем выйдет * - Какую ошибку вы получите? –

+0

это ошибка: слишком мало аргументов – fluter

ответ

3

Решение состоит из подкласса argparse.ArgumentParser и переопределения его метода error(). Фактически, после ошибки ArgumentParser вызывает свой метод error(). Затем пользовательский анализ аргументов может быть выполнен через подкласс вместо argparse.ArgumentParser. Модель error() функция найдена в источнике для argparse:

def error(self, message): 
    """error(message: string) 

    Prints a usage message incorporating the message to stderr and 
    exits. 

    If you override this in a subclass, it should not return -- it 
    should either exit or raise an exception. 
    """ 
    self.print_usage(sys.stderr) 
    self.exit(2, '%s: error: %s\n' % (self.prog, message)) 

Это, например, можно поставить исключение в error(), вместо печати сообщения, так что код, вызывающий parse_args() берет проблем с пользователем параметры.

Первоначальный ответ: согласно пояснениям в комментариях, следующее не работает. Однако он обеспечивает механизм доступа к справочным сообщениям из функций вспомогательных команд:

У вас почти есть: в каждой из ваших функций *_command(args) вы можете проверить размер args и распечатать сообщение об ошибке, если их недостаточно. аргументы.

Если вы хотите использовать автоматически генерируемый помощь в ваших командных функций, вы можете получить его, передавая subparsers к каждой команде, например, так:

args.command(subparsers, args) # Instead of args.command(args) 

Каждая *_command() функция должна затем просто взять два аргумента а не один. Сгенерирована справка сгенерирована с помощью:

subparsers.choices['beaker'].print_help() # or print_usage() 

например.

в качестве альтернативы Вы можете выбрать непосредственно передать конкретный subparser каждой подкоманде рутинного *_command():

args.command(subparsers.choices[sys.argv[1]], args) 

, а затем, в каждом *_command(subparser, args), распечатайте помощь с subparser.print_help().

+0

проблема в том, что это ошибка и выход при вызове parser.parse_args(), поэтому нет возможности вызвать args.command (subparsers, args), если нет аргументов. – fluter

+1

@fluter: Я вижу. Я обновил сообщение с помощью решения. :) – EOL