2013-02-12 42 views
25

我正在使用subprocess.Popen调用,在另一个问题中,我发现我误解了Python为命令行生成参数的方式。输出由子流程调用的命令行?

我的问题
有没有办法找出实际的命令行是什么?

示例代码: -

proc = subprocess.popen(....) 
print "the commandline is %s" % proc.getCommandLine() 

你怎么会写getCommandLine

回答

41

这取决于您使用的Python版本。 In Python3.3时,ARG被保存在proc.args

proc = subprocess.Popen(....) 
print("the commandline is {}".format(proc.args)) 

在Python2.7,the args not saved,它只是传递到其他功能,如_execute_child。所以,在这种情况下,要获得命令行的最好方法是保存它时,你就会明白:

proc = subprocess.Popen(shlex.split(cmd)) 
print "the commandline is %s" % cmd 

需要注意的是,如果你有参数的列表(如类型

In [14]: import subprocess 

In [15]: import shlex 

In [16]: cmd = 'foo -a -b --bar baz' 

In [17]: shlex.split(cmd) 
Out[17]: ['foo', '-a', '-b', '--bar', 'baz'] 

In [18]: subprocess.list2cmdline(['foo', '-a', '-b', '--bar', 'baz']) 
Out[19]: 'foo -a -b --bar baz' 
+0

我在2.6。在2.6中,至少list2cmdline是没有记录的,因为它不起作用:'--arg = foo bar'python ACTUALLY所做的是'--arg ='foo bar'',但是list2cmdline给出的是'' --arg = foo bar“'...但是,谢谢。 – 2013-02-12 16:49:56

+0

我认为问题不在'list2cmdline',而是'shlex.split'。 'shlex.split(' - arg =“foo bar”')'返回一个包含单个项目的列表:'['--arg = foo bar']',while'shlex.split(' - arg =“ foo bar“')'正确地分割参数:'['--arg','=','foo bar']'。在后面的列表中'list2cmdline'工作正常。 – unutbu 2013-02-12 16:58:26

+0

顺便说一句,只要'args'不是一个字符串,Python2.6的'subprocess'模块就会使用'list2cmdline'将'args'转换为列表,因此它的工作原理就是您所看到的作为' list2cmdline(args)'正是传递给'execvp *'或Windows等价物的东西。 – unutbu 2013-02-12 17:04:04

2

正确回答我的问题其实是,有:由shlex.split(cmd)返回的东西,那么你可以使用未公开的函数subprocess.list2cmdline恢复命令行字符串,cmd IS没有命令行。子进程的重点在于它通过IPC完成所有工作。 list2cmdline尽可能地接近预期,但实际上最好的办法是查看“args”列表,并且只知道这将是被调用程序中的argv。

+2

['list2cmdline()'](https:// hg.python.org/cpython/file/f38489a3394f/Lib/subprocess.py#l541)仅在Windows上适用于与MS C运行时分析命令行方式兼容的应用程序。它将参数列表转换为传递给'CreateProcess()'的字符串。 ['cmd.exe'使用不同的规则](http://stackoverflow.com/q/27864103/4279)。在POSIX上,列表直接传递给'os.execve()'(+/- os.fsencode())。 – jfs 2015-02-05 16:55:45