所以我有 2 个具有相同文件的目录,除了目录 a 是今天的数据,目录 b 是昨天的数据。我想要做的是比较文件并将结果输出到 3 列中,这将是文件名、文件是否相同以及文件相同的天数。
到目前为止我所拥有的是:
ls ./dropzone_current > files.txt
is_identical=false
filename="files.txt"
while read -r line
do
name="$line"
declare -i counter
diff -qs ./dropzone_current/$name ./dropzone_backup/$name
if [ $? -ne 0 ]
then
is_identical=false
counter=0
printf '%s\t%s\t%s\n' "$name" "$is_identical" "$counter" >> test.txt
else
counter=$((counter + 1))
is_identical=true
printf '%s\t%s\t%s\n' "$name" "$is_identical" "$counter" >> test.txt
fi
done < "$filename"
本质上,除了柜台之外,一切都正常。我需要计数器对于正在比较的每个文件名都是唯一的,然后在每次运行脚本时更新(每天一次),但我无法弄清楚如何做到这一点。
答案1
根据对我的其他答案和您的问题的评论,听起来您真正正在寻找的是一种跟踪一组文件更改的方法。这通常称为版本(或修订)控制。通常安装在系统上的一种常见引擎是git
。
为了实现这一点,选择一个位置来存储我们称之为“存储库”的位置,它将存储文件的副本并跟踪其中的所有更改。我们将这个位置称为/path/to/repository
。创建该目录,然后运行命令git init
。这将设置存储库。将文件复制到目录中,我们现在将当前状态“提交”到存储库:
git add *
git commit -m "Initial commit of files"
然后,您可以简单地查看交付位置并根据需要更新存储库:
#!/bin/bash
repo='/path/to/repository'
dropbox='/path/to/delivery/'
cd $repo
for file in *; do
if ! diff "${repo}/$file" "${dropbox}/$file"; then
cp -p "${dropbox}/$file" ${repo}/
git add "$file"
fi
done
git commit -m "Update for $(date)"
这是一个快速而肮脏的脚本,不能很好地处理名称中带有空格的文件,或者从提要中添加或删除的文件,但它是一个起点。
答案2
如果您希望它在多次运行脚本时保持状态,则需要将文件拖放到磁盘或其他一些非易失性介质上,脚本将在启动时读取该文件以进行初始化,并在退出时写入以供将来参考:
#!/bin/bash
dropfile='/path/to/your/counterfile'
if [[ -r "$dropfile" ]]; then
counter=$(cat "$dropfile" )
else
counter=0
fi
trap 'echo $counter > "$dropfile"' EXIT
echo "This script has run $counter times."
counter=$((counter+1))
答案3
我会建立一个版本控制系统。例如,使用mercurial,hg init
在存储文件的目录中。然后每天一次(可能作为cron
新文件放置在那里之后的一项工作),hg addremove
并且hg commit
.
然后要运行报告,您可以循环每个文件 ( for filename in dropzone/*; do
) 并获取最后提交的时间戳,例如hg log -l 1 --template "{date(date, '%s')}\n" "$filename"
。将为%s
您提供 UNIX 秒时间戳;您可以使用 获取当前值$(date +%s)
,减去该值,然后将其大致转换为天数。
任何 VCS(svn
、git
等)都适合您,因此只需使用您喜欢的即可。