我正在尝试使用 Python 中的docopt
模块来解析脚本的命令行参数。 此脚本可以直接调用,也可以通过使用 PyInstaller 构建的.exe调用。 我想在用法部分使用程序的实际名称,根据程序的调用方式而有所不同(请注意,这里还有更多相互排斥的选项,我已经省略了):
> py script.py
Usage:
script.py -foo <foo>
script.py -bar <bar>
...
> dist/script.exe
Usage:
dist/script.exe -foo <foo>
dist/script.exe -bar <bar>
...
我可以通过在传递给docopt的字符串上使用.format()
来做到这一点,但这变得丑陋并阻止将选项指定为模块docstring:
doc = """
Usage:
{} -foo <foo>
{} -bar <bar>
...
""".format(sys.argv[0], sys.argv[0])
args = docopt(doc, ...)
有没有更好的方法?
正如您从检查当前 master 分支中的代码中看到的那样,docopt 没有做太多事情来获取它解析和显示的字符串。
但是,它引发的 DocoptExit 异常是实际显示使用消息的内容,因此您可以对其进行猴子修补,如下所示test.py
""" Usage:
PROGRAM --foo <foo>
PROGRAM --bar <bar>
"""
import sys, docopt
class MyExit(SystemExit):
usage = ''
def __init__(self, message=''):
usage = self.usage.replace("PROGRAM",sys.argv[0])
SystemExit.__init__(self, (message + 'n' + usage).strip())
docopt.DocoptExit = MyExit
args = docopt.docopt(__doc__, version='0.0.1-alpha')
print str(args)
示例运行
bash-3.2$ python test.py
Usage:
test.py --foo <foo>
test.py --bar <bar>
bash-3.2$ python test.py --foo foo
{'--bar': False,
'--foo': True,
'<bar>': None,
'<foo>': 'foo'}