问题

在对某应用代码文件进行版本备份过程中,tar命令报错:

/bin/tar: app/util: file changed as we read it

导致命令返回值非0,备份脚本失败退出。

分析

根据提示,可以看到是因为在tar打包的过程中,文件发生了变动,导致tar命令的返回值不为0,但实际上,tar命令的执行时成功的,因此,可以忽略掉此报错。

解决

翻阅tar命令手册,找到以下控制warning信息的说明:

Controlling Warning Messages
NOTE
--warning=keyword
Control display of the warning messages identified by keyword. If keyword starts with the prefix no-, such messages are suppressed. Otherwise, they are enabled.

需要屏蔽的是文件修改的报错:

file-changed
`%s: file changed as we read it'

所以,只需要在打包命令中增加以下参数即可:
--warning=no-file-changed
完整的打包命令类似如下:

/bin/tar --warning=no-file-changed -zcvf /path/to/bak/archive.tar.gz \
    --exclude '*.pyc' --exclude .git -C /path/to/app target_dir_name

扩展

General Synopsis of tar
从上面的tar手册中,可以查到,tar命令的退出值会有三种情况:

0 - Successful termination.
1 - Some files differ.
2 - Fatal error

在返回值为1的时候,还有以下情况
当使用 --compare (--diff, -d) 调用tar命令的时候,表示tar包中的文件与磁盘上对应的文件不一致。
当使用--create, --append or --update参数时候,表示打包过程中,文件有变化,导致无法打包准确的文件内容。
所以当返回值为1的时候,可以认为tar命令还是能够正确打包完成,
只不过可能无法包含最终准确的内容而已,可以认为这个时候tar命令结果还是正常的。
因此可以通过忽略返回值为1的情况,参考以下信息:

tar: file changed as we read it
  set +e 
  tar -czf sample.tar.gz dir1 dir2
  exitcode=$?

  if [ "$exitcode" != "1" ] && [ "$exitcode" != "0" ]; then
      exit $exitcode
  fi
  set -e
最后修改:2020 年 02 月 13 日
如果觉得我的文章对你有用,请随意赞赏