Necesito limpiar una carpeta periódicamente. Me sale una lista de archivos que contiene texto, qué archivos están permitidos. Ahora tengo que eliminar todos los archivos que no están en este archivo.
Ejemplo:
dont-delete.txt:
dontdeletethisfile.txt
reallyimportantfile.txt
neverdeletethis.txt
important.txt
Mi carpeta de limpieza contiene esto como ejemplo:
ls /home/me/myfolder2tocleanup/:
dontdeletethisfile.txt
reallyimportantfile.txt
neverdeletethis.txt
important.txt
this-can-be-deleted.txt
also-waste.txt
never-used-it.txt
Entonces estos archivos deben ser eliminados:
this-can-be-deleted.txt
also-waste.txt
never-used-it.txt
Busco algo para crear un comando de eliminación con una opción para excluir algunos archivos proporcionados por archivo.
command-line
bash
scripts
rm
stefan83
fuente
fuente

Respuestas:
El
rmcomando se comenta para que pueda verificar y verificar que funciona según sea necesario. Entonces simplemente descomente esa línea.La
check directorysección se asegurará de que no ejecute accidentalmente el script desde el directorio incorrecto y bloquee los archivos incorrectos.Puede eliminar la
echo deletinglínea para que se ejecute en silencio.fuente
lsy la captura inútil de la salida degrepsi todo lo que quiere saber es si hubo una coincidencia o no. También utilicé patrones de cadenas fijas para evitar problemas de escape.whilebucle a unforbucle que ha cambiado inadvertidamente eliteration keydeiaf. en la declaración, que rompió el código. Lo arreglé.f. ;-P (... y +1 por su respuesta que olvidé antes)Este script de Python puede hacer esto:
Parte importante es descomentar la
os.unlink()función.NOTA : agregue este script y
dont-delete.txta sudont-delete.txtpara que ambos estén en la lista, y manténgalos en el mismo directorio.fuente
setbúsqueda en lugar de una lista para O (1) en lugar de O (n) en la segunda parte.Aquí hay una frase:
lsimprime todos los archivos en el directorio actual (en orden)sort dont_deleteimprime todos los archivos que no queremos eliminar en orden<()operador convierte una cadena en un objeto similar a un archivocommcomandos comparan dos archivos ordenados previamente e imprimen líneas en las que difieren-2 -3marcas hacecommque solo se impriman las líneas contenidas en el primer archivo pero no en el segundo, que será la lista de archivos que son seguros de eliminartail +2llamada es solo para eliminar el encabezado de lacommsalida, que contiene el nombre del archivo de entradaxargsque convertirá la secuencia de salida en una lista de argumentos pararm. La-popción obligaxargsa pedir confirmación antes de ejecutar.fuente
FWIW parece que puedes hacer esto de forma nativa
zsh, usando el(+cmd)calificador global.Para ilustrar, comencemos con algunos archivos
y un archivo de lista blanca
Primero, lea la lista blanca en una matriz:
o tal vez mejor
(el equivalente de bash
mapfileincorporado - o su sinónimoreadarray). Ahora podemos comprobar si existe una clave (nombre de archivo) en la matriz${keepfiles[(I)filename]}que devuelve 0 si no se encuentra ninguna coincidencia:Podemos usar esto para hacer una función que devuelva
truesi no hay coincidencias$REPLYen la matriz:Finalmente, usamos esta función como calificador en nuestro comando:
o, en tu caso
(Es probable que desee agregar el nombre del archivo de la lista blanca en sí).
fuente
Suponiendo que su shell bash tiene el
extglobshoptconjunto activado, aquí hay una alternativa algo más conservadora:(... ¡acompañando la sugerencia de comunicación excelente de @ gardenhead!)
fuente
A menos que la salida
ls /home/me/myfolder2tocleanup/exceda el límite máximo de argumento de shellARG_MAXque es de alrededor de 2 MB para Ubuntu, sugeriría lo siguiente.Una implementación de comando de una línea que hará el trabajo sería la siguiente:
dont-delete.txtarchivo en el directorio que contiene los archivos que se eliminarán de la siguiente manera:cdal directorio que contiene los archivos que se eliminarán de la siguiente manera:fuente
Sugiero utilizar la
rsyncsolución publicada aquí ; de lo contrario, use la solución a continuación con una condición excepcional mencionada.Suponiendo que no haya espacios en blanco (espacios / pestañas) en los archivos que figuran en un archivo llamado
excludelist, entonces haría lo siguiente:Simplemente agregue
-deleteal comando anterior para eliminar los archivos que no existen en el archivo excludelist . Si su hallazgo no tiene-deleteopción que puede utilizarrmcon-execla siguiente manera:O usar
-execcon+terminador en su lugar.echosolo se usa para correr en seco.fuente
Mi sugerencia es:
Actualizar 2018-08-07
Ejemplo:
Tenga en cuenta que después de la línea 3 tendrá el
dont-delete.txtarchivo con contenido:(el liderazgo
./es muy importante )Los archivos
cydserán eliminados.fuente