使用Python中用户插入的文件运行Linux shell脚本

时间:2017-02-06 09:04:21

标签: python linux input ffmpeg ffprobe

我正在尝试使用Python中用户输入文件预定义的ffprobe命令。然后我将使用此命令生成的文件在更有条理的视图中报告一些参数。我的代码是:

import subprocess
import json

cmd = "ffprobe -v quiet -print_format -show_format -show_streams /path/to/input/file.mp4 > output.json" 
subprocess.call(cmd.split())

with open('output.json') as json_data:
        data = json.load(json_data)
        json_data.close()
        d = float((data["streams"][0]["duration"]))
        t = (data["streams"][0]["time_base"])
        fps = [float(x) for x in t.split('/')]
        print "==========================General=========================="
        print "Name of the File: %s" %(data["format"]["filename"])
        print "Duration: %.2f minutes" %(d/60)
        print "Frame Rate: %d fps" %fps[1]
        print "Bitrate: %.2f Mbps" %(float(data["format"]["bit_rate"])/1000000)

我正在考虑使用:input_file = ("Please enter the path to your input file: ")然后在我的代码的第二行使用ffprobe命令中的input_file。但我不确定如何在引号内做到这一点。另请注意,文件名还应包含input.mp4之类的扩展名。

2 个答案:

答案 0 :(得分:0)

Shell重定向(>)仅在shell=True传递给subprocess.call()时才有效。通常你应该避免这样做,特别是如果你将用户输入作为执行命令的一部分,在这种情况下你需要确保用户输入被正确转义,例如使用shlex.qutoe()

不是在shell中使用重定向,而是可以打开要在python中写入的文件并将其作为stdout传递,或者如果您不需要该文件,则可以使用subprocess.check_output()代替subprocess.call()

input_filename = raw_input("Please enter the path to your input file: ")
cmd = ['ffprobe', '-v', 'quiet', '-print_format', 'json', '-show_format', '-show_streams',
       input_filename]

returned_data = subprocess.check_output(cmd)
data = json.loads(returned_data.decode('utf-8'))    # assuming the returned data is utf-8 encoded

...

或者使用文件写入:

input_filename = raw_input("Please enter the path to your input file: ")
cmd = ['ffprobe', '-v', 'quiet', '-print_format', 'json', '-show_format', '-show_streams',
       input_filename]

with open('output.json', 'wb') as outfile:
    subprocess.call(cmd, stdout=outfile)

with open('output.json', 'r') as infile:
    data = json.load(infile)

...

在这种情况下,输入文件名不需要引用,因为它不会被shell解释。

答案 1 :(得分:0)

这应该有效:

#!/usr/bin/env python
import subprocess
import json

input_file = raw_input("Please enter the input file path: ")

returned_data = subprocess.check_output(['ffprobe', '-v', 'quiet', '-print_format', 'json', '-show_format', '-show_streams', input_file])
data = json.loads(returned_data.decode('utf-8'))