Compara recursivamente dos directorys con diff -r sin salida en enlaces rotos

Estoy usando diff -rab para comparar recursivamente los directorys a y b . Sin embargo, a menudo sucede que existen algunos enlaces rotos (los mismos enlaces rotos en los directorys a y b que apuntan a los mismos objectives no existentes).

diff luego emite posts de error para esos casos y salidas con un código de salida distinto de cero; sin embargo, me gustaría que permanezca en silencio, y salga con 0 ya que los directorys son los mismos en mi libro.

¿Cómo puedo hacer eso?

Para la versión 3.3 o posterior de diff , debe usar la --no-dereference , como se describe en la respuesta de Pete Harlan .

Desafortunadamente, las versiones anteriores de diff no admiten ignorar enlaces simbólicos :

Algunos files no son directorys ni files regulares: son files inusuales como enlaces simbólicos, files especiales del dispositivo, canalizaciones con nombre y conectores. Actualmente, diff trata enlaces simbólicos como files regulares; trata otros files especiales como files regulares si se especifican en el nivel superior, pero simplemente informa su presencia cuando compara directorys. Esto significa que el patch no puede representar cambios en dichos files. Por ejemplo, si cambia a qué file apunta un enlace simbólico, diff genera la diferencia entre los dos files, en lugar del cambio al enlace simbólico.

diff debería informar opcionalmente cambios a files especiales especialmente, y el patch debería extenderse para comprender estas extensiones.

Si todo lo que quiere es verificar una rsync (y presumiblemente corregir lo que falta), entonces podría simplemente ejecutar el command rsync por segunda vez. Si no quiere hacer eso, entonces puede ser suficiente sumr el directory .

Si realmente quiere hacer esto con diff , puede usar find para omitir los enlaces simbólicos, y ejecutar diff en cada file individualmente. Pase sus directorys a y b como arguments:

 #!/bin/bash # Skip files in $1 which are symlinks for f in `find $1/* ! -type l` do # Suppress details of differences diff -rq $f $2/${f##*/} done 

o como un trazador de líneas:

 for f in `find a/* ! -type l`;do diff -rq $fb/${f##*/};done 

Esto identificará los files que difieren en el contenido, o los files que están en a, pero no en b .

Tenga en count que:

  • ya que estamos omitiendo enlaces simbólicos por completo, esto no se notará si los nombres de enlaces simbólicos no están presentes en b . Si lo requería, necesitaría un segundo pase de búsqueda para identificar todos los enlaces simbólicos y luego verificar explícitamente su existencia en b .
  • Los files adicionales en b no se identificarán, ya que la list se construye a partir del contenido de a . Esto probablemente no sea un problema para su escenario rsync .

Desde la versión 3.3 GNU diff no admite desreferencer enlaces simbólicos, pero luego compara las routes a las que apuntan.

Instale diffutils GNU> = 3.3 y use la --no-dereference ; no hay una opción corta para eso.

El diagnóstico será silencioso si es igual o:

Los enlaces simbólicos /tmp/noderef/a/symlink y /tmp/noderef/b/symlink diferentes

Puede usar una versión más nueva de diff

La diff en GNU diffutils 3.3 incluye una --no-dereference que le permite comparar los enlaces simbólicos en sí mismos en lugar de sus objectives. Informa si difieren, es silencioso si están de acuerdo y no les importa si están rotos.

No sé cuándo se agregó la opción; no está presente en 2.8.1.