2017-08-05 104 views
2

我想創建一個函數來執行python腳本,同時在控制檯輸出正在執行時存儲它。如何在從控制檯存儲實時輸出的同時運行python腳本?

例如,我使用subprocess模塊​​來運行example.py,但我只在整個腳本運行後才接收控制檯輸出,而不是在發生控制檯輸出時收到控制檯輸出。換句話說,按照下面的腳本,我希望立即收到控制檯輸出「hello world」,然後等待60秒,然後接收控制檯輸出「再見世界」

example.py

import time 

print "hello world!" 
time.sleep(60) 
print "goodbye world" 

下面是運行在example.py腳本和存儲後

import subprocess 
script = open('example.py',"r+").read() 
process = subprocess.Popen(['python', '-'], stdin=subprocess.PIPE, stdout=subprocess.PIPE, stderr=subprocess.PIPE) 
process.stdin.write(script) 
stored_console_output, stored_console_output_error = process.communicate() 
print stored_console_output 

這將返回整個腳本已被執行之後下一個字符串控制檯腳本

hello world! 
goodbye world 

注意:我無法更改python腳本example.py。我只能改變調用它的函數。

除了獲得控制檯輸出生活(如果可能),我想獲得導致該控制檯輸出的python行。例如,我想達到以下

import time 

print "hello world!" 
hello world 
time.sleep(60) 
print "goodbye world" 
goodbye world 

我也試着使用sys模塊,但它不保存的控制檯輸出:

import sys 
import inspect 

class SetTrace(object): 
    def __init__(self, func): 
     self.func = func 

    def __enter__(self): 
     sys.settrace(self.func) 
     return self 

    def __exit__(self, ext_type, exc_value, traceback): 
     sys.settrace(None) 

def monitor(frame, event, arg): 
    if event == "line": 
     print event 
    return monitor 


with SetTrace(monitor): 
    exec(open('example.py',"r+").read()) 

這將返回以下和它活着。

line 
line 
line 
hello world! 
line 
line 
goodbye world 
line 

回答

0

This post主要回答你的問題,雖然有特別提供關鍵看你的具體問題one comment:你打電話example.py時防止sleep() STDOUT緩衝需要-u標誌。

從上述答案大量舉債,這種解決方案的工作原理:

from subprocess import Popen, PIPE 

def execute(cmd): 
    popen = Popen(cmd, stdout=PIPE, universal_newlines=True) 
    for stdout_line in iter(popen.stdout.readline, ""): 
     yield stdout_line 
    popen.stdout.close() 

for statement in execute(['python', '-u', 'example.py']): 
    print(statement, end="") 

輸出:

Hello 
# pauses for the number of sleep seconds 
Goodbye 
相關問題