我的程序应包含以下选项,由argparse正确解析:
[-h, --help]
和[-v, --version]
[-f FILE, --file FILE]
和[-u URL, --url URL]
--url
,则可选:[-V, --verbose]
--file
或--url
,则需要[-F, --format FORMAT]
所需的使用模式为:
prog.py [-h] [-v] [-f FILE (-F FORMAT) | -u URL [-V] (-F FORMAT) ]
-F
要求适用于互斥组的两个成员
不确定它是否是positional。
所以应该可以运行:
prog.py -u "http://foo.bar" -V -F csv
并且解析器尖叫,以防我忘记-F
(正如他应该的那样)。
到目前为止我做了什么:
parser = ArgumentParser(decription='foo')
group = parser.add_mutually_exclusive_group()
group.add_argument('-f','--file', nargs=1, type=str, help='')
group.add_argument('-u','--url', nargs=1, type=str, help='')
parser.add_argument('-V','--verbose', action='store_true', default=False, help='')
parser.add_argument('-F','--format', nargs=1, type=str, help='')
由于它在没有命令行参数的情况下运行“vanilla模式”,因此所有参数都必须是可选的。
如何在我的代码中实现第3点和第4点?
编辑:
我尝试-f
和-u
作为子分析符,如here所述,但子命令似乎被视为位置,如果我在没有参数的情况下运行它,解析器会给我一个error: too few arguments
。
答案 0 :(得分:5)
使用nargs = 2和元组metavar近似于你的目标
parser = argparse.ArgumentParser(prog='PROG')
group = parser.add_mutually_exclusive_group()
group.add_argument('-f','--file', nargs=2, metavar=('FILE','FORMAT'))
group.add_argument('-u','--url', nargs=2, metavar=('URL','FORMAT'))
parser.add_argument('-V','--verbose', action='store_true',help='optional with url')
产生:
usage: PROG [-h] [-f FILE FORMAT | -u URL FORMAT] [-V]
optional arguments:
-h, --help show this help message and exit
-f FILE FORMAT, --file FILE FORMAT
-u URL FORMAT, --url URL FORMAT
-V, --verbose optional with url
这需要格式以及文件名或网址,它不需要-F
。正如其他人所指出的-V
案例中可以忽略-f
。
我尝试使用-f和-u作为subparsers,如此处所述,但是子命令似乎被视为位置,并且解析器给我一个错误:如果我在没有参数的情况下运行它,则参数太少。
在最新版本中,子命令不再被视为必需的位置。据我所知,这是更改错误消息的副作用,以提供更多信息。而不是_parse_known_args
做一个:
if positionals:
self.error(_('too few arguments'))
它会扫描_actions
以查看哪些是必需的,然后在错误消息中按名称列出它们。这在http://bugs.python.org/issue9253中讨论。我知道这个变化正在开发中(3.4),也可能在3.3中。
答案 1 :(得分:2)
当存在特定选项时,可以使用callback方法在optparse
中强制执行这些点。
但是,在argparse
中,这些不可用。
您可以为url
和file
子选项添加subparser,然后单独解析这些选项。
来自帮助:
请注意,parse_args()返回的对象只包含其属性 命令行选择的主解析器和子解析器 (而不是任何其他子分子)。所以在上面的例子中,当a命令时 指定时,只有foo和bar属性存在,并且当b命令时 如果指定,则仅存在foo和baz属性。
但我会恰当地记录用法,只是忽略那些没有的论据 适用。
e.g。让这两个命令行的行为完全相同:
prog.py -f FILE -V
prog.py -f FILE