我正在尝试设置一个sh
每 30 分钟运行一次的脚本。在每次运行期间,我想检查目录中是否存在至少一个 .RAW 文件。找到该文件扩展名后,我将执行其他代码,但现在我无法确定要使用的正确 if 语句。
我知道这个代码示例不是最理想的方法,但这是我尝试过的代码,这显然是错误的:
cd ./dir/
if [ ! -f "*.RAW"]; then
echo "No files!"
else
echo "Yes files!"
fi
如何正确测试 .RAW 扩展名是否存在?
答案1
和zsh
:
files=(*.RAW(DN))
if (($#files)); then
echo Yes
else
echo No
fi
如果你只对常规的正如您所暗示的,文件(或常规文件的符号链接)-f
是:
file=(*.RAW(ND-.))
反而。
POSIXly:
has_regfiles_by_extension() {
for ext do
for file in .*."$ext" ."$ext" *."$ext"; do
[ -f "$file" ] && return
done
return 1
done
}
if has_regfiles_by_extension RAW raw; then
echo YES
else
echo NO
fi
如果你想使用ls
,你可以这样做:
if ls -Aq | grep -q '\.RAW$'; then
echo yes
else
echo no
fi
好处之一是,如果目录不可读,您将收到一条错误消息(而不是在 shell glob 的情况下被默默忽略)。
答案2
您的示例答案几乎是正确的。首先,您需要将测试字符串".RAW"
与结束字符串分开]
:
if [ ! -f "*.RAW" ];
在这种情况下,您可以通过在引号之外加上星号来进行 shell 通配。所以完成的命令将是:
if [ ! -f *".RAW" ];
但是,如果您想这样做,这种方法就没那么有用了使用文件.RAW
。如果是这种情况,我会比较目录中每个文件的扩展名,如下所示:
for file in "test/"*; do
if [ "${file##*.}" = "RAW" ]; then
echo "Found raw file"
fi
done
Bash 语法 ${var##*.} 是您可以进行的巧妙 shell 参数扩展的一部分。您可以在以下位置找到更多信息:GNU 网站。
答案3
感谢您的所有帮助,尽管我无法让其中一些发挥作用。
然而,我确实成功地实现了我在另一个问题的答案中找到的代码! (https://unix.stackexchange.com/a/87476)
export DIR=./folder
if ls ${DIR}/*.RAW &>/dev/null
then
echo "Yes!"
else
echo "No!"
fi
答案4
两种 Bourne Shell 解决方案
使用 Bourne shell(不支持数组或 shell 选项,例如空球或者失败全局)您必须解决这样一个事实:如果未找到 glob,则将返回非零退出状态或 glob 本身。例如:
if [ -n "`ls *.RAW 2> /dev/null`" ]; then
echo "At least one RAW file found!"
else
echo "No RAW files found."
fi
一般来说,不应依赖于LS命令,但这对于您的用例来说已经足够了,并且可以解决 Bourne shell 的限制。如果您确实只想使用 shell 内置函数,则必须使用赋值并显式测试 glob 本身作为错误条件。例如:
files=*.RAW
if [ "$files" = "*.RAW" ]; then
echo "No RAW files found."
else
echo "At least one RAW file found!"
fi