Come installo una chiamata di sottoprocesso a un file di testo?


93
subprocess.call(["/home/myuser/run.sh", "/tmp/ad_xml",  "/tmp/video_xml"])

Adesso ho uno script che eseguo. Quando lo eseguo e colpisce questa riga, inizia a stampare materiale perché run.sh contiene delle stampe.

Come faccio a reindirizzare anche questo a un file di testo? (E anche stampare, se possibile)

Risposte:


171

Se vuoi scrivere l'output su un file puoi usare l' argomento stdout di subprocess.call.

Ci vuole None, subprocess.PIPE, un oggetto file o di un descrittore di file. Il primo è il valore predefinito, lo stdout viene ereditato dal genitore (il tuo script). Il secondo ti consente di passare da un comando / processo a un altro. Il terzo e il quarto sono ciò che vuoi, per avere l'output scritto su un file.

Devi aprire un file con qualcosa di simile opene passare l'oggetto o il descrittore di file intero a call:

f = open("blah.txt", "w")
subprocess.call(["/home/myuser/run.sh", "/tmp/ad_xml",  "/tmp/video_xml"], stdout=f)

Immagino che qualsiasi oggetto simile a un file funzionerebbe, come un socket (sussulto :)), ma non ho mai provato.

Come Marcog menziona nei commenti che potresti voler reindirizzare anche stderr, puoi reindirizzarlo nella stessa posizione di stdout con stderr=subprocess.STDOUT. Anche uno qualsiasi dei valori sopra menzionati funziona, puoi reindirizzare a luoghi diversi.


5
perché subprocess.call (["echo", "1", ">>", "t.txt"]) funziona?
StackOverflowOfficial

7
@Goldname hai bisogno di una shell per fare il reindirizzamento, quindi: subprocess.call(["echo", "1", ">>", "t.txt"], shell=True)dovrebbe funzionare.
Wes Mason

@WesMason Grazie, ma pensavo che subprocess.call funzionasse in un modo che era fondamentalmente come copiare e incollare nella shell?
StackOverflowOfficial

2
@Goldname nah, tutto nel sottoprocesso si basa sulla classe Popen sottostante, che apre un processo, shell = True forza l'esecuzione del processo nella shell predefinita del sistema (ad esempio / bin / sh su sistemi POSIX, che di solito è bash o dash ), è più sicuro in questo modo poiché non sei aperto a tutte le funzionalità extra fornite dalla shell (un intero linguaggio di programmazione a sé stante, con i suoi exploit se si passano i dati forniti dall'utente). Controlla anche shlex.quotese stai passando dati potenzialmente sporchi a una subshell.
Wes Mason

4
Dobbiamo chiudere il file anche dopo aver finito? questo chiude il file dopo che abbiamo finito: with open("blah.txt","w") as f: subprocess.call(["/home/myuser/run.sh", "/tmp/ad_xml", "/tmp/video_xml"], stdout=f) @Skurmedel
Alper

18

Le opzioni per popenpossono essere utilizzate incall

args, 
bufsize=0, 
executable=None, 
stdin=None, 
stdout=None, 
stderr=None, 
preexec_fn=None, 
close_fds=False, 
shell=False, 
cwd=None, 
env=None, 
universal_newlines=False, 
startupinfo=None, 
creationflags=0

Così...

subprocess.call(["/home/myuser/run.sh", "/tmp/ad_xml",  "/tmp/video_xml"], stdout=myoutput)

Quindi puoi fare quello che vuoi con myoutput(che dovrebbe essere un file btw).

Inoltre, puoi fare qualcosa di più vicino a un'uscita convogliata come questa.

dmesg | grep hda

sarebbe:

p1 = Popen(["dmesg"], stdout=PIPE)
p2 = Popen(["grep", "hda"], stdin=p1.stdout, stdout=PIPE)
output = p2.communicate()[0]

Ci sono molte informazioni utili e belle sulla pagina di manuale di Python .

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.