Python 命令行界面中的 Tab 补全 - 如何捕获 Tab 事件

发布于 2024-08-17 08:20:36 字数 376 浏览 10 评论 0原文

我正在用 Python 编写一个小 CLI(作为 Mercurial 的扩展),并且希望支持制表符补全。具体来说,我想在提示符中捕获选项卡并显示匹配选项的列表(就像 bash 一样)。

示例:输入部分名称:

 ext*TAB*  
 extensions  
 extras

问题是我不确定如何捕获 Tab 事件。我正在使用 Mercurial 的 ui.prompt() API,它只是在底层调用 raw_input()

据我所知,raw_input() 仅在“输入”时返回,如果用户输入选项卡,则返回的字符串仅包含 "\t"

I'm writing a little CLI in Python (as an extension to Mercurial) and would like to support tab-completion. Specifically, I would like catch tabs in the prompt and show a list of matching options (just like bash).

Example: Enter section name:

 ext*TAB*  
 extensions  
 extras

The problem is I'm not sure how to catch the Tab events. I'm using the ui.prompt() API of Mercurial, which is just calling raw_input() under the hood.

As far as I know, raw_input() only returns on 'enter' and if a user enters a tab, the string returned simply includes a "\t".

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

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

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

罪歌 2024-08-24 08:20:36

为此,您可以使用 readline 模块。

我能想到的最简单的代码:

import readline
COMMANDS = ['extra', 'extension', 'stuff', 'errors',
            'email', 'foobar', 'foo']

def complete(text, state):
    for cmd in COMMANDS:
        if cmd.startswith(text):
            if not state:
                return cmd
            else:
                state -= 1

readline.parse_and_bind("tab: complete")
readline.set_completer(complete)
raw_input('Enter section name: ')

示例用法:

Enter section name: <tab>
email      errors     extension  extra      foo        foobar    stuff
Enter section name: e<tab>
email      errors     extension  extra      
Enter section name: ext<tab>
extension  extra      

除了补全之外,readline 还为您提供:

  • 行编辑
  • 按键绑定配置(包括 emacs 和 vi 模式)
  • 历史记录(向上箭头可调用以前的值)
  • 历史记录搜索、保存和加载

For that you use the readline module.

Simplest code I can think:

import readline
COMMANDS = ['extra', 'extension', 'stuff', 'errors',
            'email', 'foobar', 'foo']

def complete(text, state):
    for cmd in COMMANDS:
        if cmd.startswith(text):
            if not state:
                return cmd
            else:
                state -= 1

readline.parse_and_bind("tab: complete")
readline.set_completer(complete)
raw_input('Enter section name: ')

Example usage:

Enter section name: <tab>
email      errors     extension  extra      foo        foobar    stuff
Enter section name: e<tab>
email      errors     extension  extra      
Enter section name: ext<tab>
extension  extra      

Besides completion, readline provides you with:

  • Line editing
  • Keybinding configuration (emacs and vi modes included)
  • History (up arrow to recall previous values)
  • History searching, saving and loading
黯然#的苍凉 2024-08-24 08:20:36

您几乎肯定应该使用 cmd 模块,它已经实现了制表符补全等功能,以及可能您想要做的其他部分,使用 readline 模块等等。重新发明轮子是没有意义的。

You should almost certainly be using the cmd module, which already implements tab completion and so on, and probably other parts of what you're trying to do, using the readline module and so on. There's no point reinventing the wheel.

〆一缕阳光ご 2024-08-24 08:20:36

一个很好的例子,展示了如何与 readline 配合进行制表符补全在标准库中作为 rlcompleter 模块提供 - 您不能将其用作-is(它根据当前在 Python 的 main 和builtin 中定义的名称完成),但它显示了如何执行一般任务以及如何将其连接到 readline。

An excellent example of how to do tab-completion in cooperation with readline is supplied in the standard library as the rlcompleter module — you can't use it as-is (it completes based on names currently defined in the Python's main and builtin), but it shows how to do the general task and how to hook it up to readline.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文