You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Bash脚本find命令替换赋值变量时返回Permission denied的原因

问题根因
  • 你看到的Permission denied报错本质是find遍历到当前用户无读/执行权限的路径时,向stderr输出的标准提示,这个行为和你是否将find结果存入变量没有关联——两种写法下,只要find遍历到无权限路径都会输出这个提示。
  • 之前的写法你没有感知到这个报错,是两个Bash运行规则共同导致的:
    1. 脚本头部的-eu开启了set -e(errexit)模式:该模式下普通命令返回非0退出码时会直接终止脚本,但位于if/while/until条件判断内部的命令不受这个规则约束。你最初的find命令完全写在if判断条件内,哪怕find因为权限问题返回非0,脚本也不会异常退出,你大概率没注意到混杂在正常输出里的权限报错行。
    2. 最初的写法用管道连接find和wc -l:Bash默认关闭pipefail选项时,整条管道的退出码只取最后一个命令(也就是wc -l)的退出码,只要wc正常完成统计就返回0,完全掩盖了前序find命令执行出错的事实。
  • 当你把find结果赋值给变量的语句写在if判断外的全局作用域时,find一旦因为权限问题返回非0退出码,set -e就会立刻触发脚本终止,你看到脚本异常退出+Permission denied提示,才会误以为是新写法触发了权限问题。
  • 额外注意:你之前用的-not -path "./node_modules/*"只是过滤find最终输出的结果条目,不会阻止find进入node_modules目录遍历,如果node_modules下存在权限受限的路径,find依然会进入遍历并触发报错。
优化写法

如果要实现“查找空文件+复用结果+避免无意义报错”的需求,可以参考下面的实现:

#!/bin/bash -eu

# 1. 用-prune参数直接跳过node_modules目录,根本不进入遍历,从源头减少权限报错
# 2. 用数组存储文件列表,避免文件名包含空格、换行时出现解析错误
# 3. 不需要多次执行find,性能更好
mapfile -t empty_file_list < <(find . -path "./node_modules" -prune -o -type f -empty -print)

if [[ ${#empty_file_list[@]} -gt 0 ]]; then
  echo "[check-for-empty-files] Empty files found:"
  printf '%s\n' "${empty_file_list[@]}"
  exit 1
else
  echo "[check-for-empty-files] No empties."
fi

如果不需要显示find遍历过程中的权限类提示,可以在find命令末尾加上2>/dev/null把stderr重定向到空设备即可。

内容的提问来源于stack exchange,提问作者Curtis

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.26 18:36:21