将带有空格的文件名的脚本变量传递给外部程序(ffmpeg)失败

时间:2016-01-13 07:10:54

标签: macos bash ffmpeg

简短的故事:我试图编写一个脚本,使用FFmpeg将存储在一个目录中的许多文件转换为"标准" mp4格式并将转换后的文件保存在另一个目录中。这是一次学习体验(一个有趣的体验!)因为我还没有完成任何真正的编码,因为在IBM 370大型机上使用Pascal和FORTRAN非常流行。

本质上,脚本采用文件名,从中删除路径和扩展名,使用路径和mp4扩展名重新组装文件名,并使用一些设置参数调用FFmpeg进行转换。如果目录只包含名称中没有空格的视频文件,那么一切正常。如果文件名包含空格,则FFmpeg无法处理该文件并继续执行下一个文件。该错误表明FFMpeg仅查看到第一个空格的文件名。我已经包含了下面的脚本和输出。

感谢您提供任何帮助和建议。如果你认为我应该以另一种方式做到这一点,请务必向我提出你的建议。正如我所说,自从我做了这样的事情以来已经很久了。我虽然很享受。

我首先包含代码,然后是示例输出。

for file in ./TBC/*.mp4
    do

    echo "Start of iteration"
    echo "Full text of file name:" $file

    #Remove everything up to  "C/" (filename without path)
    fn_orig=${file#*C/}
    echo "Original file name:" $fn_orig

    #Length of file name
    fn_len=${#fn_orig}
    echo "Filename Length:" $fn_len

    #file name without path or extension
    fn_base=${fn_orig:0:$fn_len-4}
    echo "Base file name:" $fn_base

    #new filename suffix
    newsuffix=".conv.mp4"

    fn_out=./CONV/$fn_base$newsuffix
    echo "Converted file name:" $fn_out

    ffmpeg -i $file -metadata title="$fn_orig" -c:v libx264 -c:a libfdk_aac -b:a 128k $fn_out

    echo "End of iteration"
    echo
    done
echo "Script completed"

将ffmpeg行注释掉,以及./TBC目录中的两个文件,这是我得到的输出

    Start of iteration
    Full text of file name: ./TBC/Test file with spaces.mp4
    Original filename: Test file with spaces.mp4
    Filename Length: 25
    Base filename: Test file with spaces
    Converted file name: ./CONV/Test file with spaces.conv.mp4
    End of iteration

    Start of iteration
    Full text of file name: ./TBC/Test_file_with_NO_spaces.mp4
    Original file name: Test_file_with_NO_spaces.mp4
    Filename Length: 28
    Base file name: Test_file_with_NO_spaces
    Converted file name: ./CONV/Test_file_with_NO_spaces.conv.mp4
    End of iteration

    Script completed

当ffmpeg被取消注释时,我不愿意发布结果,除了声明它因错误而失败:     ./TBC/Test:没有这样的文件或目录

然后脚本继续到下一个成功完成的文件,因为它的名称中没有空格。实际文件名为"测试文件为spaces.mp4"所以你可以看到ffmpeg在单词" Test"之后停止。当它遇到空间时。

我希望这一点清晰简洁,希望有人能够指出我正确的方向。我想对这个脚本做更多的事情,例如解析子目录和忽略非视频文件等。

我期待您能给予的任何见解!

1 个答案:

答案 0 :(得分:1)

尝试引用输出文件:

ffmpeg -i "$file" ... "$fn_out"

bash根据空格分隔参数,所以你必须告诉他$ fn_out是一个参数; “”表示这是一个论点。