2010-06-26 6 views
5

Ich habe diesen Code:Python subprocess verstecken stdout und es warten zu vervollständigen

def method_a(self): 
    command_line = 'somtoolbox GrowingSOM ' + som_prop_path 
    subprocess.Popen(shlex.split(command_line)) 
    ...... 

def method_b(self): ..... 
.... 

und wie Sie alle sehen, hat method_a einen Unterprozess, der das somtoolbox Programm aufruft. Aber dieses Programm hat eine lange Zeit, und ich möchte es verstecken. Ich habe versucht:

subprocess.Popen(shlex.split(command_line), stdout=subprocess.PIPE) 

Aber es kehrte diesen Satz:

cat: record error: Broked Pipe 

(Dies ist eine Übersetzung des portugiesischen Satz: "Katze: erro de gravação: Rohr quebrado") (Ich bin aus brasilien)

Auch ich habe andere Methoden (wie method_b dort), die nach der Methode_a aufgerufen werden, und diese Methoden werden ausgeführt, bevor der Subprozess den Prozess abschließen.

Wie kann ich das stdout überhaupt verstecken (und will es nirgendwohin), und den anderen Code warten lassen, bis der Unterprozess die Ausführung beendet?

Obs: Die Somtoolbox ist ein Java-Programm, das dem Terminal die lange Ausgabe gibt. versucht:

outputTuple = subprocess.Popen(shlex.split(command_line), stdout = subprocess.PIPE).communicate() 

aber kontinuierliche Ausgabe an die Shell zurückkehrt. Hilfe!

Antwort

18

Der beste Weg, dies zu tun, ist die Ausgabe in/dev/null umleiten. Sie können das tun dies wie:

devnull = open('/dev/null', 'w') 
subprocess.Popen(shlex.split(command_line), stdout=devnull) 

Dann zu warten, bis es fertig ist, können Sie .wait() auf dem Popen-Objekt verwenden, das Sie bekommen:

devnull = open('/dev/null', 'w') 
process = subprocess.Popen(shlex.split(command_line), stdout=devnull) 
retcode = process.wait() 

retcode enthält dann die Rückgabecode des Prozesses.

ZUSÄTZLICH: Wie in den Kommentaren erwähnt, wird dies stderr nicht ausblenden. Um stderr auch zu verstecken, würden Sie es so tun:

devnull = open('/dev/null', 'w') 
process = subprocess.Popen(shlex.split(command_line), stdout=devnull, stderr=devnull) 
retcode = process.wait() 
+0

Es versteckt sich nicht –

+0

@Gabriel Vielleicht müssen Sie stderr auch umleiten? –

+0

Arbeitete! Ich danke dir sehr! –

5

Popen.communicate wird verwendet, um auf die Beendigung des Prozesses zu warten. Beispiel:

gibt ein Tupel von Strings zurück, eines für stdout und eines für stderr output.

+0

Es hat nicht funktioniert. Siehe meine letzte Phrase, um zu sehen, ob sich etwas ändert. Es ist eine Ausgabe eines Java-Programms ... siehe dort, bitte. –

+2

Fügen Sie einfach ', stderr = PIPE' hinzu. – AndiDog