我为命令行编写了钩子:
# Transforms command 'ls?' to 'man ls'
function question_to_man() {
if [[ $2 =~ '^\w+\?$' ]]; then
man ${2[0,-2]}
fi
}
autoload -Uz add-zsh-hook
add-zsh-hook preexec question_to_man
Run Code Online (Sandbox Code Playgroud)
但当我这样做时:
> ls?
Run Code Online (Sandbox Code Playgroud)
退出后man我得到:
> zsh: no matches found: ls?
Run Code Online (Sandbox Code Playgroud)
如何摆脱有关错误命令的消息?
?是zsh特有的,是单个字符的通配符.这意味着如果您键入ls? zsh尝试在当前目录中找到匹配的文件名(任何三个字母名称以"ls"开头).
有两种方法可以解决这个问题:
你(们)能做到 "?" "unspecial"引述它:ls\?,'ls?'或"ls?".
你使zsh处理不匹配的情况:
如果找不到匹配项,则默认行为是打印错误.这可以通过禁用该NOMATCH选项来更改(也NULL_GLOB不能设置):
setopt NO_NOMATCH
setopt NO_NULL_GLOB
Run Code Online (Sandbox Code Playgroud)
如果没有匹配的文件,这将使单词保持不变.
警告:在(可能不太可能)存在具有匹配名称的文件的情况下,zsh将尝试执行具有第一个匹配文件名称的命令.也就是说,如果有一个名为"lsx"的文件,那么ls?将被替换为,lsx而zsh将尝试运行它.这可能会或可能不会失败,但很可能不是所期望的效果.
这两种方法都有其优点和缺点.1.可能不是你正在寻找的东西2.每次都不起作用以及改变你的炮弹行为.
另外(正如@chepner在他的评论中指出的那样)preexec另外运行而不是命令.这意味着您可以获得帮助,ls但zsh仍会尝试运行ls?甚至lsx(或其他匹配的名称).
为避免这种情况,我建议定义一个command_not_found_handler函数而不是preexec.从zsh手册:
如果未找到外部命令但
command_not_found_handler存在函数,则shell将使用所有命令行参数执行此函数.如果成功处理命令,该函数应返回状态零,如果失败,则返回非零状态.在后一种情况下,应用标准处理:'command not found'打印到标准错误,shell退出状态127.注意,处理程序在子shell中执行,分叉执行外部命令,因此更改为目录,shell参数等对主壳没有影响.
所以这应该做的伎俩:
command_not_found_handler () {
if [[ $1 =~ '\?$' ]]; then
man ${1%\?}
return 0
else
return 1
fi
}
Run Code Online (Sandbox Code Playgroud)
如果你有很多匹配的文件名但很少错误输入命令("找不到命令"错误的常见原因)你可能想要考虑使用它:
command_not_found_handler () {
man ${1%?}
}
Run Code Online (Sandbox Code Playgroud)
这不检查"?" 最后,但只是删除任何最后一个字符(注意缺少"\"in ${1%?})并尝试man在其余字符上运行.因此,即使文件名匹配,man也将运行,除非确实存在与匹配文件同名的命令.
注意:这将干扰其他工具command_not_found_handler,例如使用command-not-foundUbuntu中的工具(如果为zsh启用).
总而言之,zsh有一个被称为小部件的小部件run-help(在Emacs模式下它默认绑定到Alt+ H)而不是man为当前命令运行.
使用run-help以上的主要优点是:
您甚至可以将其绑定到Alt+ ?以使其更相似:bindkey '^[?' run-help
| 归档时间: |
|
| 查看次数: |
630 次 |
| 最近记录: |