1 votos

Bash, aplanar un directorio multinivel mientras se renombran archivos

Sé que esto sonará un poco extraño, pero por favor ten paciencia conmigo.

El sistema de entretenimiento de mi coche parece tener un límite en la cantidad de directorios y archivos de música que reconocerá en un USB: ignorará aleatoriamente directorios o archivos para ajustarse a ese límite.

La estructura de mi directorio actual es

Biblioteca de música
 Artista1
    Álbum1
       Disco 1
          Pista1
          PistaN
      
       Disco 2
           Pista1
           PistaN
   
    Álbum2
        Pista1
        PistaN
 
 Artista2
     Álbum1
         Pista1
         PistaN

etc.

Me gustaría aplanar los directorios copiando los archivos a un directorio llamado "Flat", sin embargo, hay ocasiones en las que el nombre del archivo se duplicará, por lo que perderé algunos, además, el sistema de entretenimiento eliminará cualquier archivo después de cierto número.

Mi plan era usar algo así como

find /Música -mindepth 2 -type f -exec cp {} /Flat/"$RANDOM"_{} ';'

La idea detrás de esto es que al agregar un número aleatorio al principio del nombre de archivo, cada vez que ejecute esto, elegirá un nombre de archivo diferente, permitiendo al sistema de entretenimiento tener una selección diferente.

Sin embargo, esto intenta (y falla) crear los archivos con barras incluidas en ellos.

¿Qué puedo usar en lugar de {} para quitar la ruta del destino?

2voto

David Anderson Puntos 2189

Puedes usar -execdir en lugar de -exec, como se muestra a continuación. El comando -execdir es idéntico al comando -exec con la excepción de que el comando cp se ejecutará desde el directorio que contiene el archivo actual. El nombre de archivo sustituido por la cadena {} no contiene la ruta. (En otras palabras, el nombre de archivo sustituido por la cadena {} no está calificado.)

find /Music -mindepth 2 -type f -execdir cp {} /Flat/"$RANDOM"_{} ';'

Si deseas un número aleatorio diferente cada vez que se realice una copia, entonces es posible que necesites algo similar al comando que se muestra a continuación.

find /Music -mindepth 2 -type f -execdir bash -c 'cp "{}" "/Flat/${RANDOM}_{}"' ';'

0voto

Christopher Scott Puntos 665

Creo que amontonarlo todo en un directorio plano va a causar aún más problemas, sin mencionar la locura que será iterar a través de las pistas. Seguramente tu estéreo tiene un concepto de saltar una pista y saltar fuera de la carpeta actual cuando hayas terminado con ella. ¿La aleatorización también haría que elegir la canción que quieres encontrar sea prácticamente imposible?

Sin conocimiento de tu estéreo, conformarse con un término medio de solo 1 subdirectorio, quizás dos, probablemente (con suerte) sea una solución suficientemente buena.

Con un solo directorio probablemente querrías carpetas que sean: Nombre del Artista - Nombre del Álbum con nombres de pista de 1-01 - Título… para álbumes de múltiples discos y 01 - Título para aquellos sin. Alternativamente, puedes usar la nomenclatura de álbum de disco múltiple para todo siempre que "sin número de disco" resulte en 1. (O 0, un cero principal está bien, pero un guión principal - probablemente no está en ningún lado.)

Esto es posible pero horrendamente complicado de hacer en un script solo. Seguramente existe software para ayudarte a gestionar esto, no sé cuál es ese software. Tienes que (1) crear los subdirectorios, (2) copiar los archivos a su nueva ubicación adecuada en los subdirectorios recién creados, y (3) renombrarlos con la etiqueta del disco para que no mezcles pistas de Disco 1, Disco 2 y Disco n que de otra manera no están desambiguadas.

Puedo acercarme, y funciona para mí porque ya nombro mis archivos con formatos de Núm. de Disco-Núm. de Pista - Título cuando hay múltiples discos presentes, a pesar de que también están organizados en subcarpetas:

find . -type f |awk 'BEGIN {FS="/"}{ printf "mkdir \"/Flat/%s - %s\"; cp \"%s\" \"/Flat/%s - %s/\"", $2, $3, $0, $2, $3; print ""}'
mkdir "/Flat/DDR - DDRMAX"; cp "./DDR/DDRMAX/Disc 1/1-01 Lovin' You (Rob Searle club mix).m4a" "/Flat/DDR - DDRMAX/"
mkdir "/Flat/DDR - DDRMAX"; cp "./DDR/DDRMAX/Disc 1/1-02 Somewhere Over the Rainbow.m4a" "/Flat/DDR - DDRMAX/"
mkdir "/Flat/DDR - DDRMAX"; cp "./DDR/DDRMAX/Disc 2/2-01 Select.m4a" "/Flat/DDR - DDRMAX/"
mkdir "/Flat/DDR - DDRMAX"; cp "./DDR/DDRMAX/Disc 2/2-02 WWW.Blonde Girl (Momo mix).m4a" "/Flat/DDR - DDRMAX/"
mkdir "/Flat/Metallica - Load"; cp "./Metallica/Load/01 Ain't My Bitch.m4a" "/Flat/Metallica - Load/"
mkdir "/Flat/Metallica - Load"; cp "./Metallica/Load/02 2 X 4.m4a" "/Flat/Metallica - Load/"

Toma nota de que tomé algunas libertades con la salida, como reordenar mi salida para que se liste de forma más legible para demostrar su función.

Luego tendrías que agregar | sh al final de este comando para que haga el trabajo ejecutando los comandos enumerados aquí. Esta salida simplemente imprime una cadena para verificar que los comandos que deseas que se ejecuten actuarían de la manera que deseas.

Esta solución significa que recibirás un montón de errores de "directorio ya existe", pero solo son una molestia y no detienen el proceso.

Factible, sí. ¿Con cordura? Ehhhhhhhhhhhhhhhhhhhhhh. Depende en su mayoría de que la nomenclatura de tus archivos fuente sea rigurosamente exacta y esté bien organizada.

AppleAyuda.com

AppleAyuda es una comunidad de usuarios de los productos de Apple en la que puedes resolver tus problemas y dudas.
Puedes consultar las preguntas de otros usuarios, hacer tus propias preguntas o resolver las de los demás.

Powered by:

X