readline — GNU readline 接口 — Python 文档
readline — GNU readline 接口
readline 模块定义了许多函数来帮助完成和从 Python 解释器读取/写入历史文件。 该模块可以直接使用,也可以通过 rlcompleter 模块使用,该模块支持在交互式提示下完成 Python 标识符。 使用此模块进行的设置会影响解释器的交互式提示和内置 input() 函数提供的提示的行为。
Readline 键绑定可以通过初始化文件配置,通常是在您的主目录中的 .inputrc
。 请参阅 GNU Readline 手册中的 Readline Init File,了解有关该文件的格式和允许的构造以及 Readline 库的一般功能的信息。
笔记
底层的 Readline 库 API 可能由 libedit
库而不是 GNU readline 实现。 在 macOS 上,readline 模块检测运行时正在使用的库。
libedit
的配置文件与 GNU readline 的配置文件不同。 如果您以编程方式加载配置字符串,您可以检查 readline.__doc__
中的文本“libedit”以区分 GNU readline 和 libedit。
如果您在 macOS 上使用 editline/libedit
readline 仿真,则位于主目录中的初始化文件名为 .editrc
。 例如,~/.editrc
中的以下内容将打开 vi 键绑定和 TAB 补全:
python:bind -v
python:bind ^I rl_complete
初始化文件
以下函数与 init 文件和用户配置相关:
- readline.parse_and_bind(string)
- 执行 string 参数中提供的 init 行。 这将调用底层库中的
rl_parse_and_bind()
。
- readline.read_init_file([filename])
- 执行 readline 初始化文件。 默认文件名是最后使用的文件名。 这将调用底层库中的
rl_read_init_file()
。
行缓冲区
以下函数对行缓冲区进行操作:
- readline.get_line_buffer()
- 返回行缓冲区的当前内容(底层库中的
rl_line_buffer
)。
- readline.insert_text(string)
- 在光标位置将文本插入行缓冲区。 这会调用底层库中的
rl_insert_text()
,但会忽略返回值。
- readline.redisplay()
- 更改屏幕上显示的内容以反映行缓冲区的当前内容。 这将调用底层库中的
rl_redisplay()
。
历史档案
以下函数对历史文件进行操作:
- readline.read_history_file([filename])
- 加载 readline 历史文件,并将其附加到历史列表中。 默认文件名是
~/.history
。 这将调用底层库中的read_history()
。
- readline.write_history_file([filename])
- 将历史列表保存到 readline 历史文件,覆盖任何现有文件。 默认文件名是
~/.history
。 这将调用底层库中的write_history()
。
- readline.append_history_file(nelements[, filename])
将历史的最后 nelements 项附加到文件中。 默认文件名是
~/.history
。 该文件必须已经存在。 这将调用底层库中的append_history()
。 只有当 Python 是为支持它的库版本编译时才存在此函数。3.5 版中的新功能。
- readline.get_history_length()
readline.set_history_length(length)
- 设置或返回所需的行数以保存在历史文件中。 write_history_file() 函数通过调用底层库中的
history_truncate_file()
使用该值截断历史文件。 负值意味着无限的历史文件大小。
历史列表
以下函数对全局历史列表进行操作:
- readline.clear_history()
- 清除当前历史记录。 这将调用底层库中的
clear_history()
。 Python 函数仅在 Python 为支持它的库版本编译时才存在。
- readline.get_current_history_length()
- 返回当前历史记录中的项目数。 (这与 get_history_length() 不同,后者返回将写入历史文件的最大行数。)
- readline.get_history_item(index)
- 返回 index 处历史项的当前内容。 项目索引是从一开始的。 这将调用底层库中的
history_get()
。
- readline.remove_history_item(pos)
- 从历史中删除由其位置指定的历史项目。 该位置是从零开始的。 这将调用底层库中的
remove_history()
。
- readline.replace_history_item(pos, line)
- 用 行 替换由其位置指定的历史项目。 该位置是从零开始的。 这将调用底层库中的
replace_history_entry()
。
- readline.add_history(line)
- 将 line 附加到历史缓冲区,就好像它是最后输入的行一样。 这将调用底层库中的
add_history()
。
- readline.set_auto_history(enabled)
通过 readline 读取输入时启用或禁用对
add_history()
的自动调用。 enabled 参数应该是一个布尔值,当为真时,启用自动历史,当为假时,禁用自动历史。3.6 版中的新功能。
启动钩子
- readline.set_startup_hook([function])
- 设置或删除由底层库的
rl_startup_hook
回调调用的函数。 如果指定了 function,它将被用作新的钩子函数; 如果省略或None
,则删除任何已安装的功能。 在 readline 打印第一个提示之前不带参数调用钩子。
- readline.set_pre_input_hook([function])
- 设置或删除由底层库的
rl_pre_input_hook
回调调用的函数。 如果指定了 function,它将被用作新的钩子函数; 如果省略或None
,则删除任何已安装的功能。 在打印第一个提示之后和 readline 开始读取输入字符之前,不带参数调用钩子。 只有当 Python 是为支持它的库版本编译时才存在此函数。
完成
以下功能与实现自定义单词完成功能有关。 这通常由 Tab 键操作,可以建议并自动完成正在键入的单词。 默认情况下,Readline 设置为由 rlcompleter 用于完成交互式解释器的 Python 标识符。 如果 readline 模块与自定义完成器一起使用,则应设置一组不同的单词分隔符。
- readline.set_completer([function])
设置或删除完成器功能。 如果指定了 function,它将被用作新的完成函数; 如果省略或
None
,则删除任何已安装的完成功能。 完成函数被称为function(text, state)
,对于0
、1
、2
、...中的 state,直到它返回一个非-字符串值。 它应该返回以 text 开头的下一个可能完成。已安装的完成函数由传递给底层库中的
rl_completion_matches()
的 entry_func 回调调用。 text 字符串来自底层库的rl_attempted_completion_function
回调的第一个参数。
- readline.get_completer()
- 获取补全函数,如果没有设置补全函数,则获取
None
。
- readline.get_completion_type()
- 获取正在尝试的完成类型。 这将底层库中的
rl_completion_type
变量作为整数返回。
- readline.get_begidx()
readline.get_endidx()
- 获取完成范围的开始或结束索引。 这些索引是传递给底层库的
rl_attempted_completion_function
回调的 start 和 end 参数。 基于底层的 C readline 实现,这些值在相同的输入编辑场景中可能会有所不同。 例如:众所周知,libedit 的行为与 libreadline 不同。
- readline.set_completer_delims(string)
readline.get_completer_delims()
- 设置或获取完成的单词分隔符。 这些决定了要考虑完成的单词的开头(完成范围)。 这些函数访问底层库中的
rl_completer_word_break_characters
变量。
- readline.set_completion_display_matches_hook([function])
- 设置或删除完成显示功能。 如果指定了function,它将作为新的完成显示函数; 如果省略或
None
,则删除任何已安装的完成显示功能。 这会设置或清除底层库中的rl_completion_display_matches_hook
回调。 完成显示函数称为function(substitution, [matches], longest_match_length)
,每次匹配需要显示一次。
例子
下面的例子演示了如何使用readline模块的历史读写功能,自动从用户家目录加载并保存一个名为.python_history
的历史文件。 下面的代码通常会在用户的 PYTHONSTARTUP 文件的交互会话期间自动执行。
import atexit
import os
import readline
histfile = os.path.join(os.path.expanduser("~"), ".python_history")
try:
readline.read_history_file(histfile)
# default history len is -1 (infinite), which may grow unruly
readline.set_history_length(1000)
except FileNotFoundError:
pass
atexit.register(readline.write_history_file, histfile)
这段代码实际上是在 Python 在 交互模式 下运行时自动运行的(参见 Readline 配置 )。
以下示例实现了相同的目标,但仅通过附加新历史记录来支持并发交互会话。
import atexit
import os
import readline
histfile = os.path.join(os.path.expanduser("~"), ".python_history")
try:
readline.read_history_file(histfile)
h_len = readline.get_current_history_length()
except FileNotFoundError:
open(histfile, 'wb').close()
h_len = 0
def save(prev_h_len, histfile):
new_h_len = readline.get_current_history_length()
readline.set_history_length(1000)
readline.append_history_file(new_h_len - prev_h_len, histfile)
atexit.register(save, h_len, histfile)
以下示例扩展了 code.InteractiveConsole 类以支持历史记录保存/恢复。
import atexit
import code
import os
import readline
class HistoryConsole(code.InteractiveConsole):
def __init__(self, locals=None, filename="<console>",
histfile=os.path.expanduser("~/.console-history")):
code.InteractiveConsole.__init__(self, locals, filename)
self.init_history(histfile)
def init_history(self, histfile):
readline.parse_and_bind("tab: complete")
if hasattr(readline, "read_history_file"):
try:
readline.read_history_file(histfile)
except FileNotFoundError:
pass
atexit.register(self.save_history, histfile)
def save_history(self, histfile):
readline.set_history_length(1000)
readline.write_history_file(histfile)