为什么 bash 特殊对待以点开头的命令行?

为什么 bash 特殊对待以点开头的命令行?

我尝试在线搜索答案,但答案(如果存在)被 shell 脚本中其他点应用程序所掩盖。所以就这样吧。

编辑:原来它与Fedora的默认配置有关command_not_found_handle,因此与bash源代码无关。/编辑

我发现虽然 bash 通常会抱怨缺少命令,甚至我在命令行中输入的内容都是一个目录:

[root@localhost tmp] # mkdir test
[root@localhost tmp] # test
[root@localhost tmp] # nonexistent
bash: nonexistent: command not found...
[root@localhost tmp] # test
[root@localhost tmp] # cd test
[root@localhost test] # empty
bash: empty: command not found...
[root@localhost test] # .
bash: .: filename argument required
.: usage: . filename [arguments]
[root@localhost test] # ..

上述内容显然是有效的和预期的。但这些:

[root@localhost test] # ....
[root@localhost test] # .........................
[root@localhost test] # .whatever
[root@localhost test] # ..........whatever
[root@localhost test] # ......œę©æąðæćþóœ
[root@localhost test] # .ignored
[root@localhost test] # touch .whatever
[root@localhost test] # .whatever
[root@localhost test] # file .whatever 
.whatever: empty
[root@localhost test] # file .ignored
.ignored: cannot open '.ignored' (No such file or directory)
[root@localhost test] # .ignored
[root@localhost test] # .whatever follows is just discarded
[root@localhost test] # 

只是默默地忽略我碰巧输入的任何内容。

这并不是人们所期望的。这种行为有原因吗?

编辑:我找到了一个用例!

[root@localhost ~] # ...|cat
[root@localhost ~] # ...|nonexistent
bash: nonexistent: command not found...
[root@localhost ~] # ...|nonexistent && echo works
bash: nonexistent: command not found...
[root@localhost ~] # ...|nonexistent || echo works
bash: nonexistent: command not found...
works
[root@localhost ~] # ...|cat && echo works
works
[root@localhost ~] # ...|cat || echo works
[root@localhost ~] # 

显然,它允许人们检查可执行文件是否已打开,PATH而无需尝试运行它 - 您可以看到 cat 没有阻止。它从未被执行。

这有点可笑。玩得开心!

[root@localhost ~] # LANG=en bash --version
GNU bash, version 4.3.42(1)-release (x86_64-redhat-linux-gnu)
Copyright (C) 2013 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>

编辑2:

[root@localhost ~] # declare -f command_not_found_handle
command_not_found_handle () 
{ 
local runcnf=1;
local retval=127;
[[ $- =~ i ]] || runcnf=0;
[[ ! -S /var/run/dbus/system_bus_socket ]] && runcnf=0;
[[ ! -x '/usr/libexec/packagekitd' ]] && runcnf=0;
[[ -n ${COMP_CWORD-} ]] && runcnf=0;
if [ $runcnf -eq 1 ]; then
    '/usr/libexec/pk-command-not-found' "$@";
    retval=$?;
else
    if [[ -n "${BASH_VERSION-}" ]]; then
        printf 'bash: %scommand not found\n' "${1:+$1: }" 1>&2;
    fi;
fi;
return $retval
}

答案1

事实证明,意外行为是由于 Fedora 默认实现的command_not_found_handle.感谢@TNW 提醒我它的存在。

之后就unset command_not_found_handle按预期工作了。

我不知道这是一个错误还是一个限制。

相关内容