如何使用 argparse python 为两个类别设置不同的强制参数?
Posted
技术标签:
【中文标题】如何使用 argparse python 为两个类别设置不同的强制参数?【英文标题】:How to have different mandatory parameters for two categories using argparse python? 【发布时间】:2021-03-07 18:13:05 【问题描述】:我正在编写 python 脚本,我需要根据传递的输入参数做两件事:
push:这将调用一个 api 来发布一些数据。 status:这将调用另一个api来检查数据并在控制台上打印出详细信息。当我们使用push
参数时,我们需要始终传递这三个强制参数:
而当我们使用status
参数时,我们只需要传递这两个强制参数:
如何在 Python 中使用 argparse
以这种方式配置这些参数?我正在阅读有关此here 的更多信息,但对如何使上述内容以良好的方式工作感到困惑?使用信息也应该清楚地说明使用什么输入。
使用argparse
可以做到这一点吗?任何示例将不胜感激。一般来说,我们会为push
调用一个方法,该方法将使用这些参数,类似地,对于status
,我们将调用其他一些将使用这些参数的方法。
【问题讨论】:
是的,我认为您想在“argparse”模块中使用“子命令”。这是指向涵盖它们的文档部分的指针。这可能与您在上面链接的相同文档(可能不同版本)中,但它会将您带到子命令部分:docs.python.org/3/library/argparse.html#sub-commands 就个人而言,在有人对可能重复这个或重复那个感到高兴之前,这是我第一次看到 argparse 子命令的一个明确的简约示例,它不仅仅是“参考文档”或者,相反,写一本关于它的小说。 【参考方案1】:这是一个简单的例子,它使用带有两个子命令的 argparse:
"""
How to have different mandatory parameters for two categories
using argparse python?
"""
import argparse
import sys
def main():
"""
Description here
"""
parser = argparse.ArgumentParser(
description='Stack Overflow 64995368 Parser'
)
parser.add_argument(
"-v",
"--verbose",
help="verbose output",
action="store_true"
)
subparser = parser.add_subparsers(
title="action",
dest='action',
required=True,
help='action sub-command help'
)
# create the subparser for the "push" command
parser_push = subparser.add_parser(
'push',
help='push help'
)
parser_push.add_argument(
'environment',
type=str,
help='push environment help'
)
parser_push.add_argument(
'instance',
type=str,
help='push instance help'
)
parser_push.add_argument(
'config',
type=str,
help='push config help'
)
# create the subparser for the "status" command
parser_status = subparser.add_parser(
'status',
help='status help'
)
parser_status.add_argument(
'environment',
type=str,
help='status environment help'
)
parser_status.add_argument(
'instance',
type=str,
help='status instance help'
)
args = parser.parse_args()
if args.action == 'push':
print('You chose push:',
args.environment, args.instance, args.config)
elif args.action == 'status':
print('You chose status:',
args.environment, args.instance)
else:
print('Something unexpected happened')
if __name__ == "__main__":
try:
sys.exit(main())
except KeyboardInterrupt:
print("\nCaught ctrl+c, exiting")
各种命令行的示例输出:
$ python3 test.py
usage: test.py [-h] [-v] push,status ...
test.py: error: the following arguments are required: action
$ python3 test.py -h
usage: test.py [-h] [-v] push,status ...
Stack Overflow 64995368 Parser
optional arguments:
-h, --help show this help message and exit
-v, --verbose verbose output
action:
push,status action sub-command help
push push help
status status help
$ python3 test.py push -h
usage: test.py push [-h] environment instance config
positional arguments:
environment push environment help
instance push instance help
config push config help
optional arguments:
-h, --help show this help message and exit
$ python3 test.py push
usage: test.py push [-h] environment instance config
test.py push: error: the following arguments are required: environment, instance, config
$ python3 test.py push myenv
usage: test.py push [-h] environment instance config
test.py push: error: the following arguments are required: instance, config
【讨论】:
【参考方案2】:您可以这样做,使用set_defaults
为每个子命令分配一个处理程序。
import argparse
def push(args):
return (args.environment, args.instance, args.config)
def status(args):
return (args.environment, args.instance)
parser = argparse.ArgumentParser()
subparsers = parser.add_subparsers()
# create the parser for the push command
push_parser = subparsers.add_parser('push')
push_parser.set_defaults(func=push)
push_parser.add_argument('--environment', type=str)
push_parser.add_argument('--instance', type=str)
push_parser.add_argument('--config', type=str)
# create the parser for the status command
status_parser = subparsers.add_parser('status')
status_parser.set_defaults(func=status)
status_parser.add_argument('--environment', type=str)
status_parser.add_argument('--instance', type=str)
args = parser.parse_args(['push', '--environment=a', '--instance=b', '--config=c'])
print(args.func(args))
【讨论】:
【参考方案3】:直接使用 sys.argv 内容通常更容易。 https://www.tutorialspoint.com/python/python_command_line_arguments.htm
#! /usr/bin/env python3
import sys
s_args = sys .argv ## s_args[0] = script_name.py
def push( environment, instance, config ):
print( 'PUSH command:', environment, instance, config )
def status( environment, instance ):
print( 'STATUS command:', environment, instance )
##~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
if __name__ == '__main__':
if len( s_args ) < 4:
print( 'missing args:' )
print( ' PUSH environment instance config' )
print( ' STATUS environment instance' )
elif s_args[1] .lower() == 'push':
if len( s_args ) < 5:
print( 'missing args for PUSH command:' )
print( ' PUSH environment instance config' )
else:
push( s_args[2], s_args[3], s_args[4] )
elif s_args[1] .lower() == 'status':
if len( s_args ) < 4:
print( 'missing args for STATUS command:' )
print( ' STATUS environment instance' )
else:
status( s_args[2], s_args[3] )
else:
print( 'incorrect command:' )
print( ' PUSH environment instance config' )
print( ' STATUS environment instance' )
【讨论】:
以上是关于如何使用 argparse python 为两个类别设置不同的强制参数?的主要内容,如果未能解决你的问题,请参考以下文章
如何根据 Python 中的位置参数与 argparse 的组合设置不同的选项?
python argparse - 要么两个可选参数,要么一个都没有