“diff -r”的机器可读输出

“diff -r”的机器可读输出

是否有任何机器可读的输出用于比较两个目录diff

如果我这样做diff -rq a b我会得到:

Only in a: aa
Only in b: bb
Files a/t and b/t differ

但也许像下面这样的东西在脚本中更容易解释:

- aa
+ bb
d t

答案1

是的,diff -rq输出是不可后处理的,即使是人类面对奇怪名称的文件也是如此。例如参见:

$ ls -lFA 1 2
1:
total 20
-rw-rw-r-- 1 chazelas chazelas 5 Aug 20 10:04  a
-rw-rw-r-- 1 chazelas chazelas 2 Aug 20 10:08 'A and B'
-rw-rw-r-- 1 chazelas chazelas 5 Aug 20 10:04 'a'$'\n''b'$'\n''Only in 1: foo'
lrwxrwxrwx 1 chazelas chazelas 4 Aug 20 10:10  lsock -> sock=
lrwxrwxrwx 1 chazelas chazelas 9 Aug 20 10:04  n -> /dev/null
srwxrwxr-x 1 chazelas chazelas 0 Aug 20 10:05  sock=
lrwxrwxrwx 1 chazelas chazelas 9 Aug 20 10:06  z -> /dev/zero

2:
total 14
-rw-rw-r-- 1 chazelas chazelas  5 Aug 20 10:04  a
-rw-rw-r-- 1 chazelas chazelas  2 Aug 20 10:08 'A and B'
lrwxrwxrwx 1 chazelas chazelas 17 Aug 20 10:09  lsock -> /run/udev/control=
lrwxrwxrwx 1 chazelas chazelas  9 Aug 20 10:05  n -> /dev/zero
lrwxrwxrwx 1 chazelas chazelas  9 Aug 20 10:10  sock -> ../1/sock=
lrwxrwxrwx 1 chazelas chazelas  9 Aug 20 10:05  z -> /dev/zero
$ diff -rq 1 2
Files 1/A and B and 2/A and B differ
Only in 1: a
b
Only in 1: foo
File 1/lsock is a socket while file 2/lsock is a socket
File 1/n is a character special file while file 2/n is a character special file

亲自看看您可以从该输出中得到什么。

在这里,如果只是了解哪些文件在一个文件中,哪些文件不在另一个文件中,并且对于两者共有的文件,根据它们的类型决定如何比较它们,那么手动完成这两个任务并不困难。

例如,与zsh

zmodload zsh/stat
dirA=some/dir
dirB=some/other/dir
A_files=( $dirA/**/*(NDe['REPLY=${REPLY#$dirA/}']) )
B_files=( $dirB/**/*(NDe['REPLY=${REPLY#$dirB/}']) )

only_in_A=( ${A_files:|B_files} )
only_in_B=( ${B_files:|A_files} )
common_files=( ${A_files:*B_files} )
exact_same=()
different_type=()
different_content_regular=()
for file ($common_files) {
  stat -LsH a -- $dirA/$file && stat -LsH b -- $dirB/$file || continue
  if [[ $a[device]:$a[inode] = $b[device]:$b[inode] ]]; then
    exact_same+=( $file )
  elif [[ ${a[mode][1]} != ${b[mode][1]} ]]; then
    different_type+=( $file )
  elif [[ ${a[mode][1]} = - ]]; then
    (( a[size] == b[size] )) && cmd -s -- $dirA/$file $dirB/$file ||
      different_content_regular+=( $file )
  else
    : decide what to do with other types of files
  fi
}

(未经测试)。

然后,您最终会得到多个用于不同类型差异的数组,并且可以决定如何计算和处理差异。例如,您可以通过多种方式处理符号链接。在上面的代码中,如果$dirA/foo$dirB/foo是相同的符号链接(它们硬链接在一起),上面会将它们添加到$exact_same,但如果它们指向file,它们各自目录中的相对路径,那么它们的内容很可能不同。

相关内容