Substituição incorreta tentando renomear a extensão [duplicada]

1
    

Esta pergunta já tem uma resposta aqui:

    

Estou tentando converter todos os arquivos wav e mp3 para arquivos ogg recursivamente com o find e o FFmpeg. Eu fiz o seguinte script bash para fazer isso:

#!/usr/bin/env bash

# Converts samples to ogg

find samples \( -iname '*.wav' -o -iname '*.mp3' \) -execdir ffmpeg -i "$(basename "{}")" -qscale:a 6 "${$(basename "{}")%.*}.ogg" \;

Isso, no entanto, erros em:

${$(basename "{}")%.*}.ogg: bad substitution

Como eu precisaria formatar a última substituição para fazer com que ela devolva o nome de arquivo do arquivo com o sufixo .ogg , e por que isso não funciona?

    
por Villermen 11.06.2016 / 08:38

2 respostas

3

Você parece assumir que --execdir invoca um shell (Bash) que invoca o ffmpeg. Não é esse o caso:

   -exec command ;
          Execute  command;  true  if 0 status is returned.  All following
          arguments to find are taken to be arguments to the command until
          an  argument  consisting of ';' is encountered.  The string '{}'
          is replaced by the current file name being processed  everywhere
          it occurs in the arguments to the command, not just in arguments
          where it is alone, as in some versions of find.

ffmpeg é invocado por find e ( ffmpeg ) não sabe como lidar com sua sintaxe especial.

Gostaria apenas de criar um script bash pequeno que pudesse manipular uma conversão com base apenas no nome do arquivo de entrada e usá-lo como um parâmetro para -execdir .

    
por 11.06.2016 / 09:10
2

Eu escrevi recentemente um exemplo de colocar uma linha de uma camada em um comando find , e isso é outro caso de uso para o mesmo.

Em vez de:

find samples \( -iname '*.wav' -o -iname '*.mp3' \) -execdir ffmpeg -i "$(basename "{}")" -qscale:a 6 "${$(basename "{}")%.*}.ogg" \;

Tente:

find samples \( -iname '*.wav' -o -iname '*.mp3' \) -exec sh -c 'ffmpeg -i "$1" -qscale:a 6 "${1%.*}.ogg"' find-sh {} \;

Observe que find-sh é um texto arbitrário; na posição em que está, é definido como o $0 do shell. Isso não importa muito, mas é usado para relatórios de erros, por isso é bom ter algo descritivo lá. Eu acho que find-sh é um bom nome.

    
por 11.06.2016 / 09:44