如何检查shell脚本中是否存在文件

How to check if a file exists in a shell script

我想写一个shell脚本,检查某个文件(archived_sensor_data.json是否存在,如果存在,就删除它。按照http://www.cyberciti.biz/tips/find-out-if-file-exists-with-conditional-expressions.html,我尝试了以下方法:

1
[-e archived_sensor_data.json] && rm archived_sensor_data.json

但是,这会引发一个错误

1
[-e: command not found

当我尝试使用./test_controller命令运行生成的test_controller脚本时。代码有什么问题?


括号和-e之间缺少所需的空格:

1
2
3
4
5
6
7
#!/bin/bash
if [ -e x.txt ]
then
    echo"ok"
else
    echo"nok"
fi


这里有一种使用ls的替代方法:

1
(ls x.txt && echo yes) || echo no

如果您想隐藏ls的任何输出,所以您只看到是或否,请将stdoutstderr重定向到/dev/null

1
(ls x.txt >> /dev/null 2>&1 && echo yes) || echo no


在内部,rm命令必须测试文件是否存在,那么为什么要添加另一个测试呢?公正发行

1
rm filename

不管它在那里与否,它都会在那之后消失。使用rm-f是您不需要任何关于不存在文件的消息。

如果您需要采取一些行动,如果文件不存在,那么您必须自己测试。基于您的示例代码,在这个实例中不是这样的。


我推荐解决方案的背景是一个朋友的故事,他在他的第一份工作是清理半个构建服务器。所以基本的任务是找出一个文件是否存在,如果是这样,我们就删除它。但这条河上有几个险滩:

  • 一切都是文件。

  • 只有当脚本解决一般任务时,它们才具有真正的能力

  • 一般来说,我们使用变量

  • 我们经常在脚本中使用-f force以避免手动干预

  • 同时,love-r递归确保我们及时创建、复制和销毁。

考虑以下情况:

我们有要删除的文件:fileexists.json

此文件名存储在变量中

1
<host>:~/Documents/thisfolderexists filevariable="filesexists.json"

我们也有一个路径变量来让事情变得非常灵活

1
2
3
4
5
<host>:~/Documents/thisfolderexists pathtofile=".."

<host>:~/Documents/thisfolderexists ls $pathtofile

filesexists.json  history20170728  SE-Data-API.pem  thisfolderexists

那么让我们看看-e是否做了它应该做的。文件是否存在?

1
2
3
<host>:~/Documents/thisfolderexists [ -e $pathtofile/$filevariable ]; echo $?

0

是的。魔术。

但是,如果意外地将文件变量评估为nuffin'

1
2
3
4
5
<host>:~/Documents/thisfolderexists filevariable=""

<host>:~/Documents/thisfolderexists [ -e $pathtofile/$filevariable ]; echo $?

0

什么?它应该返回时出错…这是故事的开始文件夹被意外删除

另一种选择可能是专门测试我们所理解的"文件"

1
2
3
4
5
<host>:~/Documents/thisfolderexists filevariable="filesexists.json"

<host>:~/Documents/thisfolderexists test -f $pathtofile/$filevariable; echo $?

0

所以文件存在…

1
2
3
4
5
<host>:~/Documents/thisfolderexists filevariable=""

<host>:~/Documents/thisfolderexists test -f $pathtofile/$filevariable; echo $?

1

所以这不是一个文件,也许我们不想删除整个目录

man test有以下说法:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
-b FILE

       FILE exists and is block special

-c FILE

       FILE exists and is character special

-d FILE

       FILE exists and is a directory

-e FILE

       FILE exists

-f FILE

       FILE exists and is a regular file

...

-h FILE

       FILE exists and is a symbolic link (same as -L)