2013-07-19 49 views
17

如果我在bash中运行echo a; echo b,结果将是两个命令都运行。但是,如果我使用子进程,则会运行第一个命令,打印出整个行的其余部分。 下面的代码回声a; echo b而不是a b,我怎么得到它来运行这两个命令?在子进程中运行多个bash命令

import subprocess, shlex 
def subprocess_cmd(command): 
    process = subprocess.Popen(shlex.split(command), stdout=subprocess.PIPE) 
    proc_stdout = process.communicate()[0].strip() 
    print proc_stdout 

subprocess_cmd("echo a; echo b") 
+1

相关:这是[如何运行多个shell命令(以及可选的捕捉他们的输出)并发](http://stackoverflow.com/a/23616229/4279) – jfs

回答

37

你必须使用shell =真在子也没有shlex.split:

def subprocess_cmd(command): 
    process = subprocess.Popen(command,stdout=subprocess.PIPE, shell=True) 
    proc_stdout = process.communicate()[0].strip() 
    print proc_stdout 

subprocess_cmd('echo a; echo b') 

回报:

a 
b 
+1

啊我看到,我测试了shell = True,但command.split() (列表)。另外要注意其他人的阅读,使用'shell = True'是一个安全隐患,确保你相信输入。 – Paul

+2

你不能在'shell = True'中使用'command.split()'。实际上'subprocess.Popen'与'shell = True'的参数必须是一个字符串而不是一个列表。 – bougui

+0

我发现这样会更简单一些,并且没有输出的瑕疵:def do_shell(self,command): self.proc = subprocess.Popen(command,shell = True) self.proc.wait( ) –

0
>>> command = "echo a; echo b" 
>>> shlex.split(command); 
    ['echo', 'a; echo', 'b'] 

所以,问题是shlex模块不处理 “;”

+0

command.split()给出'['echo','a;','echo','b']'并且失败。 ' – Paul

+1

@bougui是对的。设置“shell = True”,Popen的第一个参数需要一个像“echo a; echo b”这样的命令字符串。如果没有“shell = True”,Popen的第一个参数应该是一个列表,如:[“echo”,“a”] –

13

我只是无意中发现了一个情况我需要运行一个一堆线python中的bash代码(不能用分号分隔)。在这种情况下,提出的解决方案不会有帮助。一种方法是保存一个文件,然后用Popen运行它,但在我的情况下是不可能的。

我最终什么事做的是一样的东西:

commands = ''' 
echo "a" 
echo "b" 
echo "c" 
echo "d" 
''' 

process = subprocess.Popen('/bin/bash', stdin=subprocess.PIPE, stdout=subprocess.PIPE) 
out, err = process.communicate(commands) 
print out 

所以我首先创建子bash进程后,我告诉它如何执行。这种方法消除了直接将命令传递给构造函数的限制。

+1

'subprocess.check_output(commands,shell = True)'工作得很好。如果在命令中有bash-isms,则传递'executable ='/ bin/bash''。 – jfs

+1

对于Python 3,您可能想要使用:'out,err = process.communicate(commands.encode('utf-8'))'和print(out.decode('utf-8'))' –

4

通过“& &”加入命令。

os.system('echo a > outputa.txt && echo b > outputb.txt') 
+1

第二个命令不会运行,如果第一个命令有错误。我会说使用一个;代替。 – NateW

1

如果你只运行一次拍摄的命令,那你可以只使用subprocess.check_output方便的功能:

def subprocess_cmd(command): 
    output = subprocess.check_output(command, shell=True) 
    print output