Tengo una carpeta que contiene una cierta cantidad de archivos que tienen enlaces duros (en la misma carpeta o en otro lugar), y quiero des-enlazar estos archivos, para que se vuelvan independientes, y los cambios en su contenido no afectarán otro archivo (su recuento de enlaces se convierte en 1).
A continuación, doy una solución que básicamente copia cada enlace duro a otra ubicación, luego lo vuelvo a colocar en su lugar.
Sin embargo, este método parece bastante tosco y propenso a errores, por lo que me gustaría saber si hay algún comando que desvincule un archivo para mí.
Respuesta cruda:
Busque archivos que tengan enlaces duros ( Editar : para buscar también sockets, etc. que tengan enlaces duros , use find -not -type d -links +1
):
find -type f -links +1 # files only
find -not -type d -links +1 # files, sockets etc.
Un método burdo para desenlazar un archivo (copiarlo a otra ubicación y moverlo hacia atrás):
Editar: Como dijo Celada, es mejor hacer un cp -p a continuación, para evitar perder marcas de tiempo y permisos. Editar: cree un directorio temporal y cópielo en un archivo debajo de él, en lugar de sobrescribir un archivo temporal, minimiza el riesgo de sobrescribir algunos datos, aunque el mv
comando sigue siendo riesgoso (gracias @Tobu). Editar: intente crear el directorio temporal en el mismo sistema de archivos (@MikkoRantalainen).
# This is unhardlink.sh
set -e
for i in "$@"; do
temp="$(mktemp -d -- "${i%/*}/hardlnk-XXXXXXXX")"
[ -e "$temp" ] && cp -ip "$i" "$temp/tempcopy" && mv "$temp/tempcopy" "$i" && rmdir "$temp"
done
Entonces, para desvincular todos los enlaces duros ( Editar : cambiado -type f
a -not -type d
, ver arriba):
find -not -type d -links +1 -print0 | xargs -0 unhardlink.sh
cp -i
interruptor, me escupió algunos mensajes preguntándome si debería anular ./fileXXXXXX
(el $temp
archivo), aunque tmpfile debería dar nombres de archivo únicos, por lo que debe ser algún tipo de condición de carrera o lo que sea, y con el riesgo de perder algunos datos.
unhardlink.sh
debe crear el directorio temporal en el mismo directorio que contiene el archivo que necesita ser unhardlinked. De lo contrario, su llamada recursiva puede repetirse dentro de otro sistema de archivos y terminará moviendo cosas sobre los límites del sistema de archivos porque su directorio temporal está en el directorio de trabajo actual. Supongo que podrías pasar "$(dirname "$i")/hardlink-XXXXXX"
como argumento a mktemp en su lugar.
fuse
sistema de archivos, en realidad podría enviarse path/to/hardlink-XXX
a un medio de almacenamiento físico diferente path/to/original-file
, pero no hay mucho que se pueda hacer al respecto.