I’m new to bash and writing a shell script to add some metadata to music files and there are some spaces in filename
FFMPEG_TARGET_COMMAND="\"$INPUT_DIRECTORY\" $SOME_METADATA_ARG \"$OUTPUT_DIRECTORY\""
echo $FFMPEG_TARGET_COMMAND
> "/user/musicEx/Dream In Drive.mp3" \
-metadata album="soundtrack" \
-codec copy "/user/output/Dream In Drive.mp3"
ffmpeg -i $FFMPEG_TARGET_COMMAND
and I got "/user/musicEx/Dream: No such file or directory
But if I execute in shell by typing
ffmpeg -i "/user/musicEx/Dream In Drive.mp3" \
-metadata album="soundtrack" \
-codec copy "/user/output/Dream In Drive.mp3"
this will work
I wonder why. I’ve already escape the quote in $FFMPEG_TARGET_COMMAND. I tried to escape space character, but it didn’t work too.
also, I tried to put all of them into one variable:
COMMAND="ffmpeg -i \"/user/musicEx/SCARLET NEXUS.mp3\" -codec copy \"/user/output/SCARLET NEXUS.mp3\""
and I execute it by $COMMAND
So, in script, how to deal with files that have spaces in their names?
>Solution :
Use bash arrays.
SOME_METADATA_ARGS=( -metadata album="soundtrack" )
ffmpeg_args=( "$INPUT_DIRECTORY" "${SOME_METADATA_ARGS[@]}" -codec copy "$OUTPUT_DIRECTORY" )
ffmpeg -i "${ffmpeg_args[@]}"
how to deal with files that have spaces in their names when passing it to a command
Properly quote variable expansions to prohibit word splitting expansion. Check your scripts with shellcheck. It’s not what you put in the variable, it’s how you use the variable. Read https://mywiki.wooledge.org/BashFAQ/020 and
https://mywiki.wooledge.org/BashFAQ/050 .
No reason to SHOUT_THAT_MUCH. Prefer to use lower case variables for local non-exported variables.