2017-08-05 110 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 
相关问题