将文字字符串从 python-vim 脚本发送到 tmux 窗格
Send literal string from python-vim script to a tmux pane
我通过以下方式一起使用 Vim (8.0) 和 tmux (2.3):在 tmux 会话中,我有一个 window 拆分为 2 个窗格,一个窗格有一些文本文件在 Vim 中打开,另一个窗格有一些我想向其发送文本行的程序。一个典型的用例是将行从 Python 脚本发送到另一个窗格中的 IPython 会话 运行。
我正在通过使用 python 的 Vim 脚本执行此操作,代码片段示例(假设目标 tmux 窗格为 0):
py import vim
python << endpython
cmd = "print 1+2"
vim_cmd = "silent !tmux send-keys -t 0 -l \"" + cmd + "\"" # -l for literal
vim.command(vim_cmd)
endpython
这很好用,除非 cmd
有一些必须转义的字符,例如 %
、#
、$
等。 cmd
变量是从 Vim 打开的文本文件的当前行读取的,所以我可以做类似 cmd = cmd.replace('%', '\%')
等的事情,但这有两个缺点:首先,我不知道所有必须转义的 vim 字符,因此到目前为止一直在反复试验,其次,字符 "
未正确转义 - 即在字符串 Vim 中,"
就消失了,即使我这样做 cmd = cmd.replace('"', '\"')
。
那么,有没有一种通用的方法可以告诉 Vim 不解释任何内容,只获取原始字符串并按原样发送?如果不是,为什么 "
没有正确转义?
Vim脚本
您正在查找 shellescape()
函数。如果使用 :!
Vim 命令,则 {special}
参数需要为 1。
silent execute '!tmux send-keys -t 0 -l ' . shellescape(cmd, 1)
但是由于您对(显示)shell 输出不感兴趣,并且不需要与启动的脚本进行交互,我会从 :!
切换到较低级别的 system()
命令。
call system('tmux send-keys -t 0 -l ' . shellescape(cmd))
Python
使用Python(而不是纯Vim脚本)没有任何好处(至少在您问题的小片段中)。相反,如果您将 Python cmd
变量嵌入到 Vim 脚本表达式中,现在您还需要一个 Python 函数来将值转义为 Vim 脚本字符串(类似于 '%s'" % str(cmd).replace("'", "''"))
)。或者,您可以在 Vim 变量中维护该值,并通过 vim.vars
.
从 Python 访问它
我通过以下方式一起使用 Vim (8.0) 和 tmux (2.3):在 tmux 会话中,我有一个 window 拆分为 2 个窗格,一个窗格有一些文本文件在 Vim 中打开,另一个窗格有一些我想向其发送文本行的程序。一个典型的用例是将行从 Python 脚本发送到另一个窗格中的 IPython 会话 运行。
我正在通过使用 python 的 Vim 脚本执行此操作,代码片段示例(假设目标 tmux 窗格为 0):
py import vim
python << endpython
cmd = "print 1+2"
vim_cmd = "silent !tmux send-keys -t 0 -l \"" + cmd + "\"" # -l for literal
vim.command(vim_cmd)
endpython
这很好用,除非 cmd
有一些必须转义的字符,例如 %
、#
、$
等。 cmd
变量是从 Vim 打开的文本文件的当前行读取的,所以我可以做类似 cmd = cmd.replace('%', '\%')
等的事情,但这有两个缺点:首先,我不知道所有必须转义的 vim 字符,因此到目前为止一直在反复试验,其次,字符 "
未正确转义 - 即在字符串 Vim 中,"
就消失了,即使我这样做 cmd = cmd.replace('"', '\"')
。
那么,有没有一种通用的方法可以告诉 Vim 不解释任何内容,只获取原始字符串并按原样发送?如果不是,为什么 "
没有正确转义?
Vim脚本
您正在查找 shellescape()
函数。如果使用 :!
Vim 命令,则 {special}
参数需要为 1。
silent execute '!tmux send-keys -t 0 -l ' . shellescape(cmd, 1)
但是由于您对(显示)shell 输出不感兴趣,并且不需要与启动的脚本进行交互,我会从 :!
切换到较低级别的 system()
命令。
call system('tmux send-keys -t 0 -l ' . shellescape(cmd))
Python
使用Python(而不是纯Vim脚本)没有任何好处(至少在您问题的小片段中)。相反,如果您将 Python cmd
变量嵌入到 Vim 脚本表达式中,现在您还需要一个 Python 函数来将值转义为 Vim 脚本字符串(类似于 '%s'" % str(cmd).replace("'", "''"))
)。或者,您可以在 Vim 变量中维护该值,并通过 vim.vars
.