1 May 2014

Unix: recursively change file suffixes

Task

I want to move all files under a folder with names like
The Scabs\Royalty In Exile (2007 Re-Issue)\01 Crime Wave 1.m4a
to
The Scabs\Royalty In Exile (2007 Re-Issue)\01 Crime Wave.m4a
 
Reason: I have transferred my iTunes library from apple lossless encoding (ALAC) to AAC fromat, so Windows Media player can read them as well. The AAC files in iTunes have the same suffix (because AAC and apple lossless are both MP4 with a different codec). So for the new AAC file, iTunes adds ablank and an ordinal number to the file basename and appends the same m4a suffix.
I now want to replace the original ALAC files with AAC

Steps

  1. I did not find a decent windows command and did not want to learn Windows powershell so I installed Cygwin
  2. Run:
 find . -name \*\ 1.m4a -execdir sh -c 'mv -f "$1"  "${1% 1.m4a}.m4a"' _ {} \;


 Explanations:
  • -execdir: in contrast with the POSIX -exec option, execdir executes in the directory where the file is found and substitutes the unqualified filename
  • We pass the find filename placeholder {} to the shell the be able to use bash shell variables $1, which allow operations like removing a suffix using the ${1%suffix} construct
  • The behaviour of the sh -c (execute a single shell command) with respect to the first parameter ($0, normally the script name), is somewhat unreliable, so we pass in a dummy placeholder "_" for $0 and pass the find parameter {} to $1
Excellent resource on using find