Bash Find Command – Get Directory of Found File

findosxshell

I have a parent folder named "parent_folder" with a lot of subfolders, in these subfolders is a file named "foo.mp4".

I can find these files easily by doing this:

mymacbook:parent_folder username$ find ./ -name "foo.mp4" -exec echo {} \;

Now that returns the path of each file, relative to parent_folder/

./path/to/foo.mp4

How can i return just the path, without the filename?

Best Answer

With GNU find:

 find . -name foo.mp4 -printf '%h\n'

With other finds, provided directory names don't contain newline characters:

 find . -name foo.mp4 | sed 's|/[^/]*$||'

Or:

 find . -name foo.mp4 -exec dirname {} \;

though that means running one dirname command per file.

If you need to run a command on that path, you can do (standard syntax):

 find . -name "featured.mp4" -exec sh -c '
   for file do
     dir=${file%/*}
     ffmpeg -i "$file" -c:v libvpx -b:v 1M -c:a libvorbis "$dir" featured.webm
   done' sh {} +

Though in this case, you may be able to use -execdir (a BSD extension also available in GNU find), which chdir()s to the file's directory:

 find . -name "featured.mp4" -execdir \
   ffmpeg -i {} -c:v libvpx -b:v 1M -c:a libvorbis . featured.webm \;

Beware though that while the GNU implementation of find will expand {} to ./filename here, BSD ones expand to filename. It's OK here as the filename is passed as argument to an option and is always featured.mp4 anyway, but for other usages you may have to take into account that the file name may start with - or + (and be understood as an option by the command) or contain = (and be understood as a variable assignment by awk for instance), or other characters causing this kind of problem with perl -p/n (not all of them fixed by GNU find's ./ prefix though in that case), etc, which you may have to take into account.

Related Question