【问题标题】:How to get subprocess output during its running?如何在运行过程中获取子进程输出?
【发布时间】:2012-10-29 16:26:08
【问题描述】:

我有两个文件 main.py 和 infinit.py,如下所示:

main.py

#!/usr/bin/python

import logging
import subprocess
import sys

logging.basicConfig(level=logging.INFO)


def forever():
    cmd = [sys.executable, 'infinit.py']
    while 1:
        try:
            print 'running new instance of:'
            print ' '.join(cmd)
            popen = subprocess.Popen(cmd, stdout=subprocess.PIPE,
                stderr=subprocess.PIPE, universal_newlines=True)

            for line in iter(popen.stderr.readline, ""):
                print line,
            for line in iter(popen.stdout.readline, ""):
                print line,

        except Exception as e:
            print 'Something bad happend'
            logging.error(e)


if __name__ == '__main__':
    forever()

infinit.py

#!/usr/bin/python

import logging

logging.basicConfig(level=logging.INFO)

i = 0
while 1:
    i += 1
    logging.info('i: {0}'.format(i))
    print i

我运行 main.py 并希望在我的控制台中同时查看(打印和日志记录)。 我也希望它在 windows 和 linux 上运行。 此外,它是否可以在 Windows Idle 中工作(打印和记录)?

【问题讨论】:

标签: python windows subprocess


【解决方案1】:

在你的程序的乞求处添加这一行,并放入相同的LOG_FILENAME,然后你可以使用tail -f unix命令查看输出。

import logging
logging.basicConfig(filename=LOG_FILENAME,level=logging.DEBUG, filemode = 'w+')
logging.getLogger().setLevel(logging.DEBUG)

【讨论】:

    【解决方案2】:

    我找到了两种解决方案,它们都应该适用于 Linux 和 Windows,甚至适用于 Windows Idle:

    1. 更简单:

    在父进程中打印子进程的stderr:

    #!/usr/bin/python
    
    import logging
    import subprocess
    import sys
    
    def forever():
        cmd = [sys.executable, 'infinit.py']
        while 1:
            try:
                print 'running new instance of:'
                print ' '.join(cmd)
                popen = subprocess.Popen(cmd, stdout=subprocess.PIPE,
                    stderr=subprocess.PIPE, universal_newlines=True)
    
                for line in iter(popen.stderr.readline, ""):
                    print line,
    
            except Exception as e:
                print 'Something bad happend'
                logging.error(e)
    
    if __name__ == '__main__':
        forever()
    

    现在:

    • 父打印子日志(因为默认情况下日志将消息发送到我们正在打印的标准错误和标准错误)
    • 父不打印子打印,所以:

    infinit.py

    #!/usr/bin/python
    
    import logging
    import sys
    import time
    
    logging.basicConfig(level=logging.INFO)
    
    sys.stdout = sys.stderr
    
    i = 0
    while 1:
        i += 1
        logging.info('i: {0}'.format(i))
        print i
        time.sleep(0.2)
    
    1. 这里有另一种方法:

    Intercepting stdout of a subprocess while it is running

    我的代码适应了解决方案

    main.py

    #!/usr/bin/python
    
    import logging
    import subprocess
    import sys
    
    def forever():
        CMD = [sys.executable, 'infinit.py']
        while 1:
            try:
                print 'running new instance of:'
                print ' '.join(CMD)
    
                popen = subprocess.Popen(CMD, stdout=subprocess.PIPE)
                for line in iter(popen.stdout.readline, ""):
                    print line,
    
            except Exception as e:
                print 'Something bad happend'
                logging.error(e)
            finally:
                print
    
    
    if __name__ == '__main__':
        forever()
    

    init.py

    #!/usr/bin/python
    
    import logging
    import sys
    import time
    
    
    class FlushFile(object):
        """Write-only flushing wrapper for file-type objects."""
        def __init__(self, f):
            self.f = f
        def write(self, x):
            self.f.write(x)
            self.f.flush()
    
    logging.basicConfig(level=logging.INFO)
    
    sys.stdout = FlushFile(sys.stdout)
    
    
    i = 0
    while 1:
        i += 1
        logging.info('i: {0}'.format(i))
        print i
        time.sleep(0.2)
    

    【讨论】:

      猜你喜欢
      • 2018-12-06
      • 2013-05-09
      • 1970-01-01
      • 2012-03-06
      • 1970-01-01
      • 2023-01-10
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多