Mi problema (en una secuencia de comandos con #!/bin/sh
) es el siguiente: Intento sumar todos los archivos en un directorio con fines de archivo. El archivo de suma de comprobación (en mi caso sha1) con todos los nombres de archivo debe residir en el mismo directorio. Digamos que tenemos un directorio ~/test
con archivos f1
y f2
:.
mkdir ~/test
cd ~/test
echo "hello" > f1
echo "world" > f2
Ahora calculando las sumas de verificación con
find -maxdepth 1 -type f -printf '%P\n' | xargs shasum
hace exactamente lo que quiero, enumera todos los archivos del directorio actual y calcula las sumas sha1 (la profundidad máxima se puede cambiar más adelante). La salida en STDOUT es:
f572d396fae9206628714fb2ce00f72e94f2258f f1
9591818c07e900db7e1e0bc4b884c945e6a61b24 f2
Desafortunadamente, al intentar guardar esto en un archivo con
find -maxdepth 1 -type f -printf '%P\n' | xargs shasum > sums.sha1
el archivo resultante muestra la suma de comprobación por sí mismo:
da39a3ee5e6b4b0d3255bfef95601890afd80709 sums.sha1
f572d396fae9206628714fb2ce00f72e94f2258f f1
9591818c07e900db7e1e0bc4b884c945e6a61b24 f2
y, por lo tanto, falla más tarde shasum --check
, debido al obvio problema de la modificación de archivos adicionales al guardar la última suma.
Miré a mi alrededor y al usar -p
flag for xargs
, descubrí que de alguna manera crea el archivo de salida antes de incluso ejecutar el comando find, por lo tanto, se encuentra el archivo adicional y se sumará a la suma de comprobación ...
Sé que, como solución alternativa, podría guardar la suma de comprobación en otra ubicación (directorio temporal a través de mktemp
) o excluirla en find específicamente, pero me gustaría entender por qué se comporta de la manera en que lo hace, lo que a mis ojos no es tan útil, por ejemplo, si el primer comando verificaría si el archivo de salida ya está en el disco, nunca obtendría la respuesta correcta ...
sh
son necesarias varias invocaciones. Tenga en cuenta que necesita un argumento para $0
antes {}
.
tee
ha desaparecido? Lo probé y funciona bien, también suprimí STDOUT con la adición de 1>/dev/null
. ¿Hubo algún problema con la respuesta o fue un error?
xargs
, es el propio shell el que crea este archivo, porque antes de que se ejecute cualquier comando, el shell redirige todas las entradas, salidas y canalizaciones, de modo que cuandofind
comienza el archivo de salida ya existe. Utilice en su-exec
lugar:find -maxdepth 1 -type f -exec sh -c 'shasum "$@" > sums.sha1' {} +