Get just the filename from a path in a Bash script [duplicate]
How would I get just the filename without the extension and no path?
The following gives me no extension, but I still have the path attached:
source_file_filename_no_ext=${source_file%.*}
Solution 1:
Many UNIX-like operating systems have a basename
executable for a very similar purpose (and dirname
for the path):
pax> full_name=/tmp/file.txt
pax> base_name=$(basename ${full_name})
pax> echo ${base_name}
file.txt
That unfortunately just gives you the file name, including the extension, so you'd need to find a way to strip that off as well.
So, given you have to do that anyway, you may as well find a method that can strip off the path and the extension.
One way to do that (and this is a bash
-only solution, needing no other executables):
pax> full_name=/tmp/xx/file.tar.gz
pax> xpath=${full_name%/*}
pax> xbase=${full_name##*/}
pax> xfext=${xbase##*.}
pax> xpref=${xbase%.*}
pax> echo "path='${xpath}', pref='${xpref}', ext='${xfext}'"
path='/tmp/xx', pref='file.tar', ext='gz'
That little snippet sets xpath
(the file path), xpref
(the file prefix, what you were specifically asking for) and xfext
(the file extension).
Solution 2:
basename
and dirname
solutions are more convenient. Those are alternative commands:
FILE_PATH="/opt/datastores/sda2/test.old.img"
echo "$FILE_PATH" | sed "s/.*\///"
This returns test.old.img
like basename
.
This is salt filename without extension:
echo "$FILE_PATH" | sed -r "s/.+\/(.+)\..+/\1/"
It returns test.old
.
And following statement gives the full path like dirname
command.
echo "$FILE_PATH" | sed -r "s/(.+)\/.+/\1/"
It returns /opt/datastores/sda2