我有一个构建脚本,可以更改 $PATH 中的二进制文件(它不会编辑 $PATH 本身,但它会向 $PATH 中已有的文件夹添加/删除文件)。 zsh 的自动完成功能不会更新以反映为响应构建而添加/删除的文件,因此我必须重新启动 shell 或执行内置的“rehash”shell 来告诉它更新其自动完成缓存。
我决定要自动运行 rehash,所以首先我这样做了:
build() {
~/bin/real_build && rehash
}
但是 shell 函数在它们自己的子 shell 中运行,因此 rehash 将更新子 shell 的缓存,而不是我正在使用的终端中的 shell。所以我改成这样:
alias build='~/bin/real_build && rehash'
哪个有效,除非我想传递参数来构建。如果我通过“clean”,我希望它执行:
~/bin/real_build clean && rehash
但它会这样做:
~/bin/real_build && rehash clean
所以我陷入了困境——我可以使用别名但无法传递参数,或者我可以使用函数但不让它实际更新自动完成条目。有没有办法让两者都工作?
答案1
Shell 函数不会在其自己的子 shell 中运行,除非您在函数体周围使用括号而不是通常的大括号。您的函数确实更新了我见过的每个版本的 zsh 上的可执行哈希,并且我认为没有选项可以更改此行为。
答案2
我认为source
这里可能是最好的选择。这是一个例子:
cat << EOF > foo
touch $1
chmod +x $1
rehash
EOF
foo
像这样执行:
source foo bar
如果这在您的道路上,bar
那么现在就可以完成。
答案3
shell 函数像 shell 脚本一样获取参数。"$@"
, $*
$1... $n
.所有其他操作也都有效。
尝试使用函数的参数,在本例中为$1
。
build() {
~/bin/real_build ${1} && rehash
}
""
除非您的 real_build 脚本可以作为参数处理,否则请勿使用引号。
""
与什么都没有不同。
这是创建在特定位置需要参数的“别名”的好方法。