Inicie um comando shell com um script em python, aguarde a rescisão e retorne ao script
-
11-07-2019 - |
Pergunta
Eu tenho um script python que precisa iniciar um comando Shell para cada arquivo em um diretor:
import os
files = os.listdir(".")
for f in files:
os.execlp("myscript", "myscript", f)
Isso funciona bem para o primeiro arquivo, mas depois que o comando "myscript" terminou, a execução para e não volta ao script Python.
Como eu posso fazer? Eu tenho que fork()
antes da calling os.execlp()
?
Solução
Subprocess: o
subprocess
O módulo permite gerar novos processos, conectar -se aos seus tubos de entrada/saída/erro e obter seus códigos de retorno.
http://docs.python.org/library/subprocess.html
Uso:
import subprocess
process = subprocess.Popen(command, shell=True, stdout=subprocess.PIPE)
process.wait()
print process.returncode
Outras dicas
Você pode usar subprocess.Popen
. Há algumas maneiras de fazer isso:
import subprocess
cmd = ['/run/myscript', '--arg', 'value']
p = subprocess.Popen(cmd, stdout=subprocess.PIPE)
for line in p.stdout:
print line
p.wait()
print p.returncode
Ou, se você não se importa com o que o programa externo realmente faz:
cmd = ['/run/myscript', '--arg', 'value']
subprocess.Popen(cmd).wait()
O módulo de subprocesso apareceu desde 2008. Em particular check_call
e check_output
Facilite ainda mais as coisas de subprocesso. o check_*
Família de funções é boa que eles levantam uma exceção se algo der errado.
import os
import subprocess
files = os.listdir('.')
for f in files:
subprocess.check_call( [ 'myscript', f ] )
Qualquer saída gerada por myscript
será exibido como se seu processo produzisse a saída (tecnicamente myscript
e seu script python compartilhe o mesmo stdout). Existem algumas maneiras de evitar isso.
check_call( [ 'myscript', f ], stdout=subprocess.PIPE )
O stdout será suprimido (cuidado semyscript
produz mais que 4k de saída). Stderr ainda será mostrado, a menos que você adicione a opçãostderr=subprocess.PIPE
.check_output( [ 'myscript', f ] )
check_output
Retorna o stdout como uma string para que não seja mostrada. Stderr ainda é mostrado, a menos que você adicione a opçãostderr=subprocess.STDOUT
.
o os.exec*()
funções substituir o programação atual com o novo. Quando esse programas termina o seu processo. Você provavelmente quer os.system()
.
Use Spawn
import os
os.spawnlp(os.P_WAIT, 'cp', 'cp', 'index.html', '/dev/null')
Eu uso o os.system
import os
os.system("pdftoppm -png {} {}".format(path2pdf, os.path.join(tmpdirname, "temp")))
Isso funcionou para mim bem!
shell_command = "ls -l"
subprocess.call(shell_command.split())