5

我正在使用 python 来运行一些 shell 脚本、RScripts、python 程序等。这些程序可能会运行很长时间,并且可能会向 stdout 和 stderr 输出大量(日志记录)信息。我正在使用以下(Python 2.6)代码,它工作正常:

stdoutFile=open('stdout.txt', 'a')
stderrFile=open('stderr.txt', 'a')
subprocess.call(SHELL_COMMAND, shell=True, stdout=stdoutFile, stderr=stderrFile)
stdoutFile.close()
stderrFile.close()

这主要是记录到文件中的信息,并且可以在很长一段时间内生成此信息。因此我想知道是否可以在每一行前面加上日期和时间?

例如,如果我当前要登录:

Started
Part A done
Part B done
Finished

然后我希望它是:

[2012-12-18 10:44:23] Started
[2012-12-18 12:26:23] Part A done
[2012-12-18 14:01:56] Part B done
[2012-12-18 22:59:01] Finished

注意:修改我运行的程序不是和选项,因为这个 python 代码有点像这些程序的包装器。

4

1 回答 1

5

与其向 的stdoutstderr参数提供文件subprocess.call(),不如直接创建一个Popen对象并创建PIPEs,然后在此管理器脚本中读取这些管道,并在写入所需的任何日志文件之前添加任何您想要的标签。

def flush_streams_to_logs(proc, stdout_log, stderr_log):
    pipe_data = proc.communicate()
    for data, log in zip(pipe_data, (stdout_log, stderr_log)):
        # Add whatever extra text you want on each logged message here
        log.write(str(data) + '\n')

with open('stdout.txt', 'a') as stdout_log, open('stderr.txt', 'a') as stderr_log:
    proc = subprocess.Popen(SHELL_COMMAND, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE)
    while proc.returncode is None:
        flush_streams_to_logs(proc, stdout_log, stderr_log)
    flush_streams_to_logs(proc, stdout_log, stderr_log)

请注意,communicate()阻塞直到子进程退出。您可能希望直接使用子进程的流,以便拥有更多实时日志记录,但是您必须自己处理并发和缓冲区填充状态。

于 2012-12-18T14:27:01.680 回答