Bash 脚本检测目录中文件的变化

das*_*j19 14 directory hashsum files

我正在尝试制作一个脚本,用于检测目录中的任何文件是否在 2 秒间隔内发生更改。到目前为止我所拥有的是:

#!/bin/bash
for FILE in "${PWD}/*"
do
    SUM1="$(md5sum $FILE)"
    sleep 2
    SUM2="$(md5sum $FILE)"
    if [ "$SUM1" = "$SUM2" ];
    then
        echo "Identical"
    else
        echo "Different"
    fi
done
Run Code Online (Sandbox Code Playgroud)

这仅输出一次值“相同”,我希望它检查每个文件并为每个文件输出“相同”或“不同”。

编辑:这可以在不安装inotify-tools软件包的情况下完成吗?

Rah*_*hul 15

您绝对可以从命令行使用inotify-tools,例如:

inotifywait -r  -m /dir/to/monitor/
Run Code Online (Sandbox Code Playgroud)

来自man inotifywait

-m, --monitor

不是在收到单个事件后退出,而是无限期执行。默认行为是在第一个事件发生后退出。

这是一个从 man 文件复制的连续监视脚本inotifywait

inotifywait -r  -m /dir/to/monitor/
Run Code Online (Sandbox Code Playgroud)


ter*_*don 12

正如其他人所解释的那样,使用inotify是更好的解决方案。我将解释为什么您的脚本失败。首先,无论您使用哪种语言编程,每当您尝试调试某些东西时,第一条规则是“打印所有变量”:

$ ls
file1  file2  file3
$ echo $PWD    
/home/terdon/foo
$ for FILE in "${PWD}/*"; do echo "$FILE"; done
/home/terdon/foo/*
Run Code Online (Sandbox Code Playgroud)

因此,正如您在上面看到的,$FILE实际上扩展为$PWD/*. 因此,循环只在字符串 上运行一次,/home/terdon/foo/*而不是在目录中的每个文件上单独运行。然后,md5sum命令变为:

md5sum /home/terdon/foo/*
Run Code Online (Sandbox Code Playgroud)

换句话说,它md5sum一次在目标目录中的所有文件上运行,而不是在每个文件上运行。

问题是您引用了 glob 扩展并阻止了它的扩展:

$ echo "*"
*
$ echo *
file1 file2 file3
Run Code Online (Sandbox Code Playgroud)

虽然变量几乎总是被引用,但 globs 不应该因为这使它们成为字符串而不是 globs。

你的意思是:

for FILE in "${PWD}"/*; do ...
Run Code Online (Sandbox Code Playgroud)

但是,没有理由在$PWD这里使用,它没有添加任何有用的东西。上面的行相当于:

for FILE in *; do
Run Code Online (Sandbox Code Playgroud)

另外,避免对 shell 变量使用大写字母。这些用于系统设置的环境变量,最好将自己的变量保持为小写。

考虑到所有这些,这里有一个脚本的改进版本:

$ ls
file1  file2  file3
$ echo $PWD    
/home/terdon/foo
$ for FILE in "${PWD}/*"; do echo "$FILE"; done
/home/terdon/foo/*
Run Code Online (Sandbox Code Playgroud)


maz*_*azs 5

您可以使用该inotify-tools包实时监控文件夹中的所有更改。例如,它包含inotifywait您可以使用的工具,例如:

> inotifywait /tmp
Setting up watches.
Watches established.
/tmp/ MODIFY test
Run Code Online (Sandbox Code Playgroud)

您可以使用标志来仅过滤某些事件或某些文件。该inotifywatch工具收集文件系统使用统计信息并输出每个inotify事件的计数。

例如,您可以在此处找到更多示例。

如果你想与其他工具来监控,您可以使用find-mmin参数(修改分钟)。由于 2 秒就像 0.033 分钟,您可以使用:

find . -type f -mmin 0.033
Run Code Online (Sandbox Code Playgroud)