为什么Click?

有那么多库可以用来编写命令行实用程序;为什么Click“存在”?

这个问题很容易回答:因为没有一个针对python的命令行实用程序可以勾选以下框:

  • 无拘无束

  • 支持执行unix/posix命令行约定

  • 支持将环境变量中的值从框中加载

  • 支持自定义值提示

  • 完全可嵌套且可组合

  • 支持开箱即用的文件处理

  • 附带有用的通用帮助程序(获取终端尺寸、ANSI颜色、获取直接键盘输入、屏幕清除、查找配置路径、启动应用程序和编辑器等)。

点击有很多选择;显而易见的是 optparseargparse 从标准库。看看有没有其他东西能引起你的共鸣。

click实际上实现了它自己的参数解析,并且不使用 optparseargparse 跟随 optparse 分析行为。它不基于的原因 argparse 那是 argparse 不允许通过设计正确嵌套命令,并且在符合POSIX的参数处理方面存在一些缺陷。

Click被设计成有趣和可定制的,但不是过于灵活。例如,帮助页面的可定制性受到限制。这个约束是有意的,因为Click承诺多个Click实例在串在一起时将继续按预期工作。

太多的可定制性会破坏这一承诺。

已写入Click以支持 Flask 微框架生态系统,因为没有工具能够提供它所需要的功能。

为了了解Click的所有功能,我强烈建议您查看 复杂的应用 章。

为什么不argparse?

Click内部基于 optparse 而不是 argparse . 这是一个用户不必关心的实现细节。Click不基于argparse,因为它的某些行为使处理任意命令行界面变得困难:

  • argparse有内置的行为来猜测某个东西是参数还是选项。当处理不完整的命令行时,这将成为一个问题;如果不完全了解命令行,行为将变得不可预测。这与Click将其派往二级间谍的野心背道而驰。

  • argparse不支持禁用分散参数。没有这个特性,就不可能安全地实现Click的嵌套解析。

为什么不Docopt等?

Docopt和许多类似的工具在工作方式上都很酷,但是很少有工具像Click那样处理命令嵌套和可组合性。据开发人员所知,Click是第一个Python库,旨在创建一个超出系统本身支持范围的应用程序可组合性级别。

例如,Docopt通过解析帮助页面,然后根据这些规则进行解析。这样做的副作用是docopt在处理命令行界面的方式上非常严格。docopt的优点是它可以让您对帮助页面进行强有力的控制;缺点是,由于这一点,它无法按照当前终端宽度重新包装输出,并且使翻译变得困难。除此之外,docopt仅限于基本解析。它不处理参数分派和回调调用或类型。这意味着除了处理解析结果的基本帮助页面之外,还需要编写许多代码。

然而,最重要的是,它使可组合性变得困难。虽然docopt支持分派到子命令,但它不直接支持基于可用的任何类型的自动子命令枚举,或者它不强制子命令以一致的方式工作。

这很好,但它不同于Click的工作方式。Click目标通过执行以下操作来支持完全可组合的命令行用户界面:

  • Click不只是解析,它还发送到适当的代码。

  • click有一个强大的调用上下文概念,它允许子命令响应来自父命令的数据。

  • Click具有可用于所有参数和命令的强大信息,因此它可以为完整的CLI生成统一的帮助页面,并根据需要帮助用户转换输入数据。

  • Click对什么是类型有很强的理解,如果出现错误,它可以向用户提供一致的错误消息。由不同开发人员编写的子命令不会因错误消息而突然终止,因为它是手动处理的。

  • Click拥有足够的元信息,可以让整个程序随着时间的推移而发展,并在不强迫开发人员调整程序的情况下改善用户体验。例如,如果Click决定更改帮助页面的格式,所有Click程序都将自动从中受益。

Click的目的是制造可组合的系统。然而,docopt的目标是构建最漂亮和手工制作的命令行界面。这两个目标以微妙的方式相互冲突。为了实现统一的命令行界面,Click主动阻止人们实现某些模式。例如,作为一个开发人员,在格式化帮助页面时,您几乎没有选择余地。

为什么要硬编码行为?

另一个问题是为什么Click远离optparse并硬编码某些行为,而不是保持可配置性。这有多种原因。最大的一个问题是,过多的可配置性使得很难获得一致的命令行体验。

最好的例子是Optparse的 callback 接受任意数量参数的功能。由于命令行上的语法歧义,无法实现完全可变的参数。总有一些需要权衡的地方 argparse 这些权衡已经足够关键了,像click这样的系统甚至不能在上面实现。

在这种特定的情况下,Click尝试保留一些公认的用于构建命令行接口的范例,这些范例可以很好地记录和测试。

为什么不自动更正?

问题是,既然optparse和argparse都支持长参数的自动扩展,那么Click为什么不能自动更正参数呢。这样做的原因是向后兼容性的问题。如果人们开始依赖自动修改的参数,并且将来有人添加了一个新参数,脚本可能会停止工作。这类问题很难找到,所以Click并没有试图对此感到不可思议。

但是,这种行为可以在更高的级别上实现,以支持诸如显式别名之类的事情。有关详细信息,请参阅 命令别名 .