返回介绍

公用事业

发布于 2025-05-06 21:24:12 字数 7760 浏览 0 评论 0 收藏

除了 click 提供的与参数解析和处理接口的功能外,它还提供了一系列插件功能,这些功能对于编写命令行实用程序很有用。

打印到 stdout

最明显的助手是 echo() 函数,在许多方面与 Python 类似 print 语句或函数。主要的区别在于它在 Python2 和 3 中的工作方式相同,它智能地检测错误配置的输出流,并且它永远不会失败(在 Python3 中除外;有关更多信息,请参见 python 3 限制 )

例子::

import click

click.echo('Hello World!')

最重要的是,它可以同时打印 Unicode 和二进制数据,这与内置的 print python 3 中的函数,它不能输出任何字节。但是,它将在默认情况下发出一个尾随新行,需要通过传递来抑制它 nl=False ::

click.echo(b'\xe2\x98\x83', nl=False)

最后但并非最不重要 echo() 使用 click 的智能内部输出流到 stdout 和 stderr,后者在 Windows 控制台上支持 Unicode 输出。这意味着只要你使用 click.echo 您可以输出 Unicode 字符(对于可以显示字符的默认字体有一些限制)。此功能在 Click 6.0 中是新功能。

6.0 新版功能。

现在 Click 模拟 Windows 上的输出流,以通过单独的 API 支持 Unicode 到 Windows 控制台。有关详细信息,请参阅 Windows 控制台说明 .

3.0 新版功能。

从 Click 3.0 开始,您还可以通过传递轻松打印到标准错误 err=True ::

click.echo('Hello World!', err=True)

ANSI 颜色

2.0 新版功能。

从 Click2.0 开始, echo() 函数获得了处理 ANSI 颜色和样式的额外功能。请注意,在 Windows 上,此功能仅在以下情况下可用: colorama 已安装。如果安装了它,则可以智能地处理 ANSI 代码。注意,在 python 2 中,echo 函数不解析来自 bytearray 的颜色代码信息。

这主要意味着:

  • Click 的 echo() 如果流未连接到终端,函数将自动删除 ANSI 颜色代码。
  • 这个 echo() 函数将透明地连接到 Windows 上的终端,并将 ANSI 代码转换为终端 API 调用。这意味着颜色在 Windows 上的作用与在其他操作系统上的作用相同。

注意事项 colorama 支持:Click 会自动检测 colorama 可以使用。做 not 调用 colorama.init() 你说什么?

安装 colorama ,运行此命令::

$ pip install colorama

为了设计一根绳子的样式, style() 函数可用于:

import click

click.echo(click.style('Hello World!', fg='green'))
click.echo(click.style('Some more text', bg='blue', fg='white'))
click.echo(click.style('ATTENTION', blink=True, bold=True))

结合 echo()style() 也可以在一个函数中调用 secho() ::

click.secho('Hello World!', fg='green')
click.secho('Some more text', bg='blue', fg='white')
click.secho('ATTENTION', blink=True, bold=True)

Pager 支持

在某些情况下,您可能希望在终端上显示长文本,并让用户在其中滚动。这可以通过使用 echo_via_pager() 类似于 echo() 函数,但始终通过 pager 写入 stdout 和(如果可能)。

例子:

@click.command()
def less():
    click.echo_via_pager('\n'.join('Line %d' % idx
                                   for idx in range(200)))

如果要对大量文本使用 pager,特别是如果提前生成所有内容需要花费大量时间,则可以传递生成器(或生成器函数)而不是字符串:

def _generate_output():
    for idx in range(50000):
        yield "Line %d\n" % idx

@click.command()
def less():
    click.echo_via_pager(_generate_output())

屏幕清除

2.0 新版功能。

要清除终端屏幕,可以使用 clear() 从 Click2.0 开始提供的函数。它按照名字的意思做:它以一种平台不可知论的方式清除整个可见屏幕:

import click
click.clear()

从终端获取字符

2.0 新版功能。

通常,当从终端读取输入时,您将从标准输入读取。但是,这是缓冲输入,在线路终止之前不会显示。在某些情况下,您可能不想这样做,而是在编写单个字符时读取它们。

为此,Click 提供 getchar() 从终端缓冲区中读取单个字符并将其作为 Unicode 字符返回的函数。

请注意,即使 stdin 是管道,此函数也始终从终端读取。

例子::

import click

click.echo('Continue? [yn] ', nl=False)
c = click.getchar()
click.echo()
if c == 'y':
    click.echo('We will go on')
elif c == 'n':
    click.echo('Abort!')
else:
    click.echo('Invalid input :(')

请注意,这将读取原始输入,这意味着箭头键之类的东西将以平台的本机转义格式显示。翻译的字符只有 ^C^D 分别转换为键盘中断和文件结束异常。这样做是因为否则,很容易忘记这一点并创建无法正确退出的脚本。

等待按键

2.0 新版功能。

有时,暂停直到用户按下键盘上的任何键是有用的。这在 Windows 上特别有用 cmd.exe 默认情况下,将在命令执行结束时关闭窗口,而不是等待。

在 click 中,可以通过 pause() 功能。此功能将向终端打印一条快速消息(可自定义),等待用户按键。除此之外,如果脚本不以交互方式运行,它也将成为 NOP(无操作指令)。

例子::

import click
click.pause()

启动编辑器

2.0 新版功能。

Click 支持自动启动编辑器 edit() . 这对于询问用户多行输入非常有用。它将自动打开用户定义的编辑器或返回到合理的默认值。如果用户关闭编辑器而不保存,返回值将为 None 否则输入的文本。

示例用法:

import click

def get_commit_message():
    MARKER = '# Everything below is ignored\n'
    message = click.edit('\n\n' + MARKER)
    if message is not None:
        return message.split(MARKER, 1)[0].rstrip('\n')

或者,该函数还可以用于为特定文件名的文件启动编辑器。在这种情况下,返回值总是 None .

示例用法:

import click
click.edit(filename='/etc/passwd')

启动应用程序

2.0 新版功能。

Click 支持通过 launch() . 这可用于打开与 URL 或文件类型关联的默认应用程序。例如,它可以用于启动 Web 浏览器或图片查看器。除此之外,它还可以启动文件管理器并自动选择提供的文件。

示例用法:

click.launch("https://click.palletsprojects.com/")
click.launch("/my/downloaded/file.txt", locate=True)

打印文件名

因为文件名可能不是 Unicode,所以格式化它们可能有点困难。通常,这在 Python2 中比在 3 上更容易,因为您可以用 print 函数,但在 python 3 中,您总是需要使用 unicode 操作。

使用 Click 的方式是通过 format_filename() 功能。它尽最大努力将文件名转换为 Unicode,并且永远不会失败。这使得在完整的 Unicode 字符串上下文中使用这些文件名成为可能。

例子::

click.echo('Path: %s' % click.format_filename(b'foo.txt'))

标准流

对于命令行实用程序,可靠地访问输入和输出流非常重要。python 通常通过 sys.stdout 和 friends,但不幸的是,2.x 和 3.x 之间存在 API 差异,特别是在这些流如何响应 Unicode 和二进制数据方面。

因此,Click 提供 get_binary_stream()get_text_stream() 函数,它在不同的 Python 版本和各种终端配置中产生一致的结果。

最终结果是,这些函数总是返回一个函数流对象(除了在 python 3 中非常奇怪的情况;请参见 python 3 限制 )

例子::

import click

stdin_text = click.get_text_stream('stdin')
stdout_binary = click.get_binary_stream('stdout')

6.0 新版功能。

现在 Click 模拟 Windows 上的输出流,以通过单独的 API 支持 Unicode 到 Windows 控制台。有关详细信息,请参阅 Windows 控制台说明 .

智能文件打开

3.0 新版功能。

从 click 3.0 开始,从 File 类型通过 open_file() 功能。它可以智能地打开 stdin/stdout 以及任何其他文件。

例子::

import click

stdout = click.open_file('-', 'w')
test_file = click.open_file('test.txt', 'w')

如果返回 stdin 或 stdout,返回值将包装在特殊文件中,上下文管理器将阻止关闭该文件。这使得对标准流的处理透明化,并且您始终可以这样使用它::

with click.open_file(filename, 'w') as f:
    f.write('Hello World!\n')

正在查找应用程序文件夹

2.0 新版功能。

通常,您希望打开属于应用程序的配置文件。但是,不同的操作系统根据其标准将这些配置文件存储在不同的位置。Click 提供 get_app_dir() 函数,根据操作系统为应用程序的每个用户配置文件返回最合适的位置。

示例用法:

import os
import click
import ConfigParser

APP_NAME = 'My Application'

def read_config():
    cfg = os.path.join(click.get_app_dir(APP_NAME), 'config.ini')
    parser = ConfigParser.RawConfigParser()
    parser.read([cfg])
    rv = {}
    for section in parser.sections():
        for key, value in parser.items(section):
            rv['%s.%s' % (section, key)] = value
    return rv

显示进度条

2.0 新版功能。

有时,您有需要处理大量数据的命令行脚本,但您希望快速向用户显示有关所需时间的一些进度。Click 支持简单的进度条渲染 progressbar() 功能。

基本用法非常简单:其思想是您有一个要操作的 iterable。对于 iterable 中的每个项,可能需要一些时间来进行处理。假设你有一个这样的循环:

for user in all_the_users_to_process:
    modify_the_user(user)

要将其与自动更新进度条连接起来,您只需将代码更改为:

import click

with click.progressbar(all_the_users_to_process) as bar:
    for user in bar:
        modify_the_user(user)

Click 将自动在终端上打印进度条,并计算剩余时间。计算剩余时间需要 iterable 有一个长度。如果它没有长度,但您知道长度,则可以显式提供:

with click.progressbar(all_the_users_to_process,
                       length=number_of_users) as bar:
    for user in bar:
        modify_the_user(user)

另一个有用的功能是将标签与进度条关联,进度条前面将显示:

with click.progressbar(all_the_users_to_process,
                       label='Modifying user accounts',
                       length=number_of_users) as bar:
    for user in bar:
        modify_the_user(user)

有时,可能需要迭代外部迭代器,并且不规则地推进进度条。为此,您需要指定长度(并且不可 ITerable),并对上下文返回值使用 update 方法,而不是直接在其上迭代:

with click.progressbar(length=total_size,
                       label='Unzipping archive') as bar:
    for archive in zip_file:
        archive.extract()
        bar.update(archive.size)

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。
列表为空,暂无数据
    我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。