失败
find ${settings_base} -type f -exec source {} \;
o/p
find: ‘source’: No such file or directory
通过
for f in $(find ${settings_base} -type f); do
source "${f}"
done
我只是想知道失败的原因。
-exec
的 find
谓词运行一个子流程。但是 source
不能作为子进程运行。
Shell 内置程序如
source
(和 cd
等)修改当前运行的 shell 实例的环境。它们不作为外部命令存在(没有 /bin/source
或 /usr/bin/source
),因为它们不能作为外部命令工作。回想一下,出于安全原因以及架构原因,子进程无法修改其父进程的环境(另请参阅shell 脚本中的全局环境变量了解背景)。所以事实上,即使find
可以以某种方式执行source
,它也只能修改find
进程的环境,然后当find
退出时,它的任何效果都会丢失,你的当前正在运行的 shell 实例将回到运行之前的位置 find
。
您已经发现的解决方法就是实现这一点的方法,尽管为了完全稳健性,您还必须防止
find
输出中出现空格或其他 shell 元字符。 https://mywiki.wooledge.org/BashFAQ/020 有详细的讨论,但我不会在这里重复所有的细微差别和极端情况;单击进入链接页面。
while IFS= read -r -d '' f; do
source "$f"
done < <(find $settings_base -type f -print0)
(请注意,
-print0
是 GNU 扩展,因此无法正确移植到各种非 Linux 平台。)
根据
$settings_base
包含的内容,它可能应该用双引号引起来;另请参阅 何时在 shell 变量周围加引号?