Узнайте, какие аргументы были переданы явно в argparse - PullRequest
1 голос
/ 28 октября 2019

Мне нужно обработать два способа настройки приложения. Один из них - через аргументы командной строки, а другой - из файла JSON (на самом деле файл JSON является результатом хранения аргументов из предыдущего запуска).

Я могу справиться с этим путем объединения двух пространств именобъекты, что-то вроде этого:

cli_args = some_parser.parse_args()
with open(json_file, 'r') as f:
    json_args = json.load(f)
all_args = argparse.Namespace()
all_args.__dict__ = {**vars(cli_args), **json_args}
# or all_args.__dict__ = {**json_args, **vars(cli_args)}

Проблема в последней строке. Если я выберу первую версию, аргументы из файла JSON будут иметь приоритет. Если я выберу вторую версию, аргументы из CLI будут иметь приоритет.

Я бы хотел, чтобы аргументы CLI имели приоритет, , но только , если они действительно были указаны. Проблема возникает, когда анализатор допускает значения по умолчанию. В этом случае объект cli_args будет заполнен значениями по умолчанию, и это будет иметь приоритет над аргументами JSON.

Для простого примера, давайте возьмем этот синтаксический анализатор:

parser = argparse.ArgumentParser()
parser.add_argument('--foo', default='FOO')
parser.add_argument('--bar', default='BAR')
* 1015Скажем, у меня есть файл JSON с
{
  "foo": "myfoo",
  "bar": "mybar"
}

, и я вызываю мое приложение с помощью python myapp.py --foo hello.

Я хотел бы получить объект пространства имен, имеющий foo=hello, bar=mybar. Оба способа объединения аргументов дадут что-то другое. Во-первых, если я предоставлю приоритет JSON-файлу, я получу foo=myfoo, bar=mybar. Если я даю CLI приоритет, я получаю foo=hello, bar=BAR.

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

Есть ли способ задать argparse, какие аргументы фактически были явно заданы в командной строке, а не заполнены значениями по умолчанию?

1 Ответ

0 голосов
/ 29 октября 2019

Я не смог найти способ задать argparse, какие аргументы были заданы явно, но я нашел альтернативный способ решения моей проблемы.

А именно, метод parse_args принимает объект пространства имен, который он будет заполнятьс результатами разбора. Следовательно, я могу прочитать содержимое JSON в пространство имен, а затем использовать parse_args() для добавления аргументов из командной строки. Это переопределит настройки JSON, но только для явно заданных аргументов, а не для значений по умолчанию:

json_args = argparse.Namespace()
with open(json_file, 'r') as f:
    json_args.__dict__ = json.load(f)
all_args = parser.parse_args(namespace=json_args)
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...