多个未标记参数与水泥一起使用
我正在用 cement 写一个 Python 命令行工具。Cement 在处理标准参数解析方面表现得很好。不过,我想添加一些没有标志的特定参数。让我来解释一下。
典型的命令行工具是这样的:
cmd subcmd -flag -stored=flag
现在,假设我想添加一些没有标志的参数,比如说像 cd 命令那样。
cd my/dir
my/dir
是一个没有标志的参数。
有没有办法用 cement 实现这个功能呢?
这是我目前的 cement 应用示例:
# define application controllers
class MyAppBaseController(controller.CementBaseController):
class Meta:
label = 'base'
interface = controller.IController
description = "My Application Does Amazing Things"
arguments = [
(['--base-opt'], dict(help="option under base controller")),
]
@controller.expose(help="base controller default command", hide=True)
def default(self):
self.app.args.parse_args(['--help'])
print "Inside MyAppBaseController.default()"
@controller.expose(help="another base controller command")
def command1(self):
print "Inside MyAppBaseController.command1()"
假设我想执行 myapp command1 some/dir some_string
,
有没有办法解析这些参数呢?
2 个回答
在Cement的文档中提到:“Cement定义了一个叫做IArgument的参数接口,还有一个默认的ArgParseArgumentHandler来实现这个接口。这个处理器是基于Python标准库中的ArgParse模块构建的。”
你可以通过告诉argparse模块,从参数列表中获取一个参数,并把它存储在pargs列表的name属性中来实现这个功能。
# define application controllers
class MyAppBaseController(controller.CementBaseController):
class Meta:
label = 'base'
interface = controller.IController
description = "My Application Does Amazing Things"
arguments = [
(['--base-opt'], dict(help="option under base controller")),
]
@controller.expose(help="base controller default command", hide=True)
def default(self):
self.app.args.parse_args(['--help'])
print "Inside MyAppBaseController.default()"
@controller.expose(
help="another base controller command",
arguments=[
(['path'],
dict(type=str, metavar='PATH', nargs='?', action='store', default='.')),
(['string'],
dict(type=str, metavar='STRING', nargs='?', action='store', default='')),
]
)
def command1(self):
print "Inside MyAppBaseController.command1() path: %s string: %s" % (self.app.pargs.name, self.app.pargs.string)
你可以通过在ArgParse中使用可选的位置参数来实现这个功能。实际上,GitHub上有一个关于这个主题的文档改进问题:
https://github.com/datafolklabs/cement/issues/256
简单来说,如果你想让“command1”来处理某个操作,那么“some/dir some_string”就是位置参数。你可以在MyAppBaseController.Meta.arguments中添加以下内容:
( ['extra_arguments'], dict(action='store', nargs='*') ),
然后在command
函数内部这样访问这些参数:
if self.app.pargs.extra_arguments:
print "额外参数 0: %s" % self.app.pargs.extra_arguments[0]
print "额外参数 1: %s" % self.app.pargs.extra_arguments[1]