问题描述
使用 click
时,我知道如何定义单选选项.我也知道如何将选项设置为必需.但是,如何可以指示一个选项仅需要如果选项的值是
When using click
I know how to define a multiple choice option. I also know how to set an option as a required one. But, how can I indicate that an option B
is required only if the value of option A
is foo
?
这是一个例子:
import click
@click.command()
@click.option('--output',
type=click.Choice(['stdout', 'file']), default='stdout')
@click.option('--filename', type=click.STRING)
def main(output, filename):
print("output: " + output)
if output == 'file':
if filename is None:
print("filename must be provided!")
else:
print("filename: " + str(filename))
if __name__ == "__main__":
main()
如果 output
选项是 stdout
,则不需要 filename
.但是,如果用户选择 output
作为 file
,则必须提供其他选项 filename
.点击是否支持这种模式?
If the output
option is stdout
, then filename
is not needed. However, if the user chooses output
to be file
, then the other option filename
must be provided. Is this pattern supported by click?
在函数的开头,我可以添加以下内容:
At the beginning of the function I can add something like:
if output == 'file' and filename is None:
raise ValueError('When output is "file", a filename must be provided')
但是我很感兴趣是否有更好/更清洁的解决方案.
But I am interested whether there's a nicer/cleaner solution.
推荐答案
在此示例的特定情况下,我认为一个更简单的方法是摆脱-output
,并简单地假设如果未指定-filename
,并且如果指定了-filename
,则使用 stdout
,而不是 stdout
In the particular case of this example, I think an easier method would be to get rid of --output
, and simply assume stdout
if --filename
is not specified and if --filename
is specified, then use it instead of stdout
.
但是假设这是一个人为的示例,您可以从 click.Option
继承,以允许连接到点击处理:
But assuming this is a contrived example, you can inherit from click.Option
to allow hooking into the click processing:
class OptionRequiredIf(click.Option):
def full_process_value(self, ctx, value):
value = super(OptionRequiredIf, self).full_process_value(ctx, value)
if value is None and ctx.params['output'] == 'file':
msg = 'Required if --output=file'
raise click.MissingParameter(ctx=ctx, param=self, message=msg)
return value
使用自定义类:
要使用自定义类,请将其作为cls参数传递给选项装饰器,例如:
Using Custom Class:
To use the custom class, pass it as the cls argument to the option decorator like:
@click.option('--filename', type=click.STRING, cls=OptionRequiredIf)
测试代码:
import click
@click.command()
@click.option('--output',
type=click.Choice(['stdout', 'file']), default='stdout')
@click.option('--filename', type=click.STRING, cls=OptionRequiredIf)
def main(output, filename):
print("output: " + output)
if output == 'file':
if filename is None:
print("filename must be provided!")
else:
print("filename: " + str(filename))
main('--output=file'.split())
结果:
Usage: test.py [OPTIONS]
Error: Missing option "--filename". Required if --output=file
这篇关于仅当使用click做出选择时才需要和选择的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!