zsh中的Home/End键不适用于putty

agn*_*nul 33 keyboard terminal zsh terminal-emulator

我正在运行zsh作为Ubuntu盒子上的默认shell,并且使用gnome-terminal(据我所知模仿xterm)一切正常.当我通过ssh和putty(也模仿xterm)从Windows框登录时,主/端密钥不再有效.

我已经能够解决将这些行添加到我的zshrc文件...

bindkey '\e[1~' beginning-of-line
bindkey '\e[4~' end-of-line
Run Code Online (Sandbox Code Playgroud)

......但我仍然想知道这里有什么问题.任何的想法?

hop*_*pla 66

我发现它是一个组合:

zsh的开发商并不认为ZSH应该定义的行为Home,End,Del,...键.

Debian和Ubuntu通过定义普通用户在全局/etc/zsh/zshrc文件中期望的正常操作来解决此问题.遵循相关代码(在Debian和Ubuntu上是相同的):

if [[ "$TERM" != emacs ]]; then
[[ -z "$terminfo[kdch1]" ]] || bindkey -M emacs "$terminfo[kdch1]" delete-char
[[ -z "$terminfo[khome]" ]] || bindkey -M emacs "$terminfo[khome]" beginning-of-line
[[ -z "$terminfo[kend]" ]] || bindkey -M emacs "$terminfo[kend]" end-of-line
[[ -z "$terminfo[kich1]" ]] || bindkey -M emacs "$terminfo[kich1]" overwrite-mode
[[ -z "$terminfo[kdch1]" ]] || bindkey -M vicmd "$terminfo[kdch1]" vi-delete-char
[[ -z "$terminfo[khome]" ]] || bindkey -M vicmd "$terminfo[khome]" vi-beginning-of-line
[[ -z "$terminfo[kend]" ]] || bindkey -M vicmd "$terminfo[kend]" vi-end-of-line
[[ -z "$terminfo[kich1]" ]] || bindkey -M vicmd "$terminfo[kich1]" overwrite-mode

[[ -z "$terminfo[cuu1]" ]] || bindkey -M viins "$terminfo[cuu1]" vi-up-line-or-history
[[ -z "$terminfo[cuf1]" ]] || bindkey -M viins "$terminfo[cuf1]" vi-forward-char
[[ -z "$terminfo[kcuu1]" ]] || bindkey -M viins "$terminfo[kcuu1]" vi-up-line-or-history
[[ -z "$terminfo[kcud1]" ]] || bindkey -M viins "$terminfo[kcud1]" vi-down-line-or-history
[[ -z "$terminfo[kcuf1]" ]] || bindkey -M viins "$terminfo[kcuf1]" vi-forward-char
[[ -z "$terminfo[kcub1]" ]] || bindkey -M viins "$terminfo[kcub1]" vi-backward-char

# ncurses fogyatekos
[[ "$terminfo[kcuu1]" == "^[O"* ]] && bindkey -M viins "${terminfo[kcuu1]/O/[}" vi-up-line-or-history
[[ "$terminfo[kcud1]" == "^[O"* ]] && bindkey -M viins "${terminfo[kcud1]/O/[}" vi-down-line-or-history
[[ "$terminfo[kcuf1]" == "^[O"* ]] && bindkey -M viins "${terminfo[kcuf1]/O/[}" vi-forward-char
[[ "$terminfo[kcub1]" == "^[O"* ]] && bindkey -M viins "${terminfo[kcub1]/O/[}" vi-backward-char
[[ "$terminfo[khome]" == "^[O"* ]] && bindkey -M viins "${terminfo[khome]/O/[}" beginning-of-line
[[ "$terminfo[kend]" == "^[O"* ]] && bindkey -M viins "${terminfo[kend]/O/[}" end-of-line
[[ "$terminfo[khome]" == "^[O"* ]] && bindkey -M emacs "${terminfo[khome]/O/[}" beginning-of-line
[[ "$terminfo[kend]" == "^[O"* ]] && bindkey -M emacs "${terminfo[kend]/O/[}" end-of-line
fi
Run Code Online (Sandbox Code Playgroud)

因此,如果您连接到Debian或Ubuntu框,则无需执行任何操作.一切都应该自动工作(如果没有,见下文).

但是......如果你要连接到另一个盒子(例如FreeBSD),可能没有用户友好的默认值zshrc.解决方案当然是将Debian/Ubuntu中的行添加zshrc到您自己的行中.zshrc.

Putty xterm作为终端类型发送到远程主机.但地方弄乱了,不发送正确的控制代码Home,End...这人会期望从一个xterm.或者xterm终端不会发送那些或其他任何东西......(如果你在ZSH中配置它,Del密钥确实可以工作xterm).另请注意,您的Numpad-keys在Vim中表现得很有趣,例如xterm终端.

解决方案是将Putty配置为发送另一种终端类型.我试过xterm-colorlinux.xterm-color修复Home/ End问题,但Numpad仍然很有趣.设置它来linux解决这两个问题.

您可以在连接 - >数据下的Putty中设置终端类型.不要试图将你的终端类型设置为你.zshrcexport TERM=linux,这是错误的.终端类型应由终端应用程序指定.因此,例如,如果您从Mac机箱与Mac SSH客户端连接,它可以设置它自己的终端类型.

请注意,TERM指定了您的终端类型,与您要连接的主机无关.我可以将我的终端类型设置为linuxPutty并连接到FreeBSD服务器而不会出现问题.

所以,修复这两件事你应该没事:)

  • 另一个可以修复有趣的键盘行为:打开会话设置,转到"终端 - >功能"并选中标有"禁用应用程序键盘模式"的复选框.见这里:http://the.earth.li/~sgtatham/putty/0.60/htmldoc/Chapter4.html#config-appkeypad (3认同)

Ada*_*rce 16

在PuTTY配置对话框中,转到Connection - > Data并在连接之前键入linux到Terminal-type字符串.


Zen*_*xer 9

距离这个问题首次提出已经过去近 11 年了。当时,一些发行版确实附带了puttyterminfo 条目,但它充其量只是平庸。从那以后的几年里,情况有所改善,十多年来所必需的黑客攻击已不再需要。PuTTY 仍然默认设置为TERM兼容性xterm,但如果您连接到现代的最新系统,您可能会幸运地覆盖此设置并将其设置为putty-256color

  1. 确保主机具有以下术语信息条目putty-256colortoe -a | grep -F putty
  2. 撤消您可能启用的任何黑客行为,以使 PuTTY 与 zsh 或其他程序正常工作。
  3. 确保 PuTTY 是最新的。当有更新可用时,它不会通知您,如果更新已经过时,您可能会遇到很多相同的问题。您可能希望使用Chocolatey之类的工具自动使其保持最新状态。
  4. 在 PuTTY 的配置对话框中,转到“连接”->“数据”并将“终端类型字符串”设置为putty-256color
  5. 当您执行此操作时,在同一配置屏幕上添加新的环境变量以启用 24 位颜色。该变量不是标准化的,但它是由许多其他主流终端仿真器(例如 iTerm2)发送的,并且许多程序都可以理解它。
    1. 多变的:COLORTERM
    2. 价值:truecolor
  6. 截至撰写本文时,我还没有找到默认通过 SSH 接受 COLORTERM 变量的发行版。您需要在主机上编辑 OpenSSH 配置以允许它。例如,在类似 Debian 的发行版上,编辑/etc/ssh/sshd_config并添加COLORTERM到该AcceptEnv行。
  7. 现在一切都应该“正常工作”。如果没有:
    1. 确保您在进行更改后重新连接,或者至少exec zsh在更改后运行TERMTERMzsh在运行时不会对更改做出反应。
    2. 确保TERM实际设置为您想要的:echo $TERM
    3. 您使用的是最新版本的发行版吗?例如,如果您正在进行长期支持生命周期构建,即使您的版本在技术上仍然受支持,它也可能没有最新的 terminfo 条目。
    4. 你用的是screen还是tmux?那又是一整罐蠕虫。首先进行测试,以缩小问题发生的范围。在 tmux 中,尝试设置TERM=tmux-256color. 在屏幕内,尝试TERM=screen-256color.
    5. 您使用的是最新版本的 PuTTY 吗?
    6. 您是否有实现按键绑定或其他 hack 的 RC 文件?尝试使用默认 RC 文件。
    7. 在尝试 terminfo 修复之前,您是否已更改各种 PuTTY 设置以尝试修复问题?您可能需要重置这些设置。


Ren*_*ene 6

这对我有用

bindkey -v

bindkey '\eOH'  beginning-of-line
bindkey '\eOF'  end-of-line
Run Code Online (Sandbox Code Playgroud)


Jos*_*Gee 5

应该在所有发行版中都可以移植的适当答案(虽然不一定是所有版本的 zsh,但这里是 ymmv)是使用 zkbd 的 zkbd 辅助实用程序。

键盘定义
键盘、工作站、终端、模拟器和窗口系统的大量可能组合使得 zsh 不可能为每种情况都内置键绑定。在 Functions/Misc 中找到的 zkbd 实用程序可以帮助您快速为您的配置创建键绑定。

将 zkbd 作为自动加载函数或 shell 脚本运行:

zsh -f ~/zsh-4.3.17/Functions/Misc/zkbd
Run Code Online (Sandbox Code Playgroud)

当你运行 zkbd 时,它首先要求你输入你的终端类型;如果它提供的默认值是正确的,只需按回车键。然后它会要求您按多个不同的键来确定键盘和终端的特性;如果 zkbd 发现任何异常,例如一个既不发送 ^H 也不发送 ^? 的 Delete 键,它就会警告你。

zkbd 读取的击键记录为名为 key 的关联数组的定义,写入到 HOME 或 ZDOTDIR 目录中的子目录 .zkbd 中的文件中。文件名由 TERM、VENDOR 和 OSTYPE 参数组成,并由连字符连接。

您可以将此文件读入您​​的 .zshrc 或其他带有source' or.' 的启动文件。命令,然后在 bindkey 命令中引用 key 参数,如下所示:

          source ${ZDOTDIR:-$HOME}/.zkbd/$TERM-$VENDOR-$OSTYPE
          [[ -n ${key[Left]} ]] && bindkey "${key[Left]}" backward-char
          [[ -n ${key[Right]} ]] && bindkey "${key[Right]}" forward-char
          # etc.
Run Code Online (Sandbox Code Playgroud)

请注意,为了使 `autoload zkbd' 工作,zkdb 文件必须位于 fpath 数组中指定的目录之一中(请参阅 zshparam(1))。如果你有一个标准的 zsh 安装,这应该已经是这种情况了;如果不是,请将 Functions/Misc/zkbd 复制到适当的目录。

请参阅man -P "less -p 'keyboard definition'"zshcontrib,或搜索元联机帮助页zshall