如何将stdout和stderr重定向到管道但保持有序

时间:2013-01-17 17:01:29

标签: python unix file-io posix pipe

我希望能够从子进程中独立读取stdout / stderr(以及我正在介绍的新stdlog),对这些流执行某些操作,并将它们写入屏幕并将其写入相同的日志文件中顺序。

所以,例如,如果子进程想要对stdout说“aa”,然后将“bb”改为stderr然后再将“cc”改为stdout,我想在屏幕上看到“aabbcc”。如果我看到“aaccbb”,我可以容忍它(我想它无法帮助),但我当然不希望看到“aacbbc”(写在一个bug块中的东西“cc”被拆分)。

所以,这是我提出的流程层次结构:

(P) parent process
\_ (O) logger for stdout
\_ (E) logger for stderr
\_ (C) monitored process
  • (C)stdout使用管道连接到写入日志文件和标准输出的(O)进程
  • (C)stderr使用管道连接到(E)进程写入日志文件和stderr

问题在于,根据何时安排(O)和(E),一般输出(由(O)和(E)的输出组成)可能出现故障。

我有办法吗?

  • 有完美的订购吗?我想不,但也许有一个解决方案......
  • 至少知道在(O)和(E)进程中要读取多少字节,以便我可以将它们整合在一起?

并且,最好使用python,并且可以在unices中移植。

注意:代码位于github。整个想法是捕获受监视进程的确切输出,将其存储在日志文件中。在从stderr或stdout写入输出之前写入日志文件标记,例如“\ 0err \ 0”或“\ 0std \ 0”,以便稍后我可以从进程中重新生成确切的输出,尊重stdout和stderr。

谢谢

1 个答案:

答案 0 :(得分:0)

如果将stdout和stderr重定向到同一个管道(即proc1 2>&1 | proc2),则无法控制管道上的顺序,因为它们现在完全相同。 stdout和stderr在操作系统中都有相同的路径。

“proc2”将读取数据的顺序仅取决于“proc1”写入它们的顺序。 订单仅依赖于proc1。

通常,进程会缓冲这样的数据:

    如果输出是TTY,则
  • stdout 被缓冲,但刷新每个换行符,否则当缓冲区已满时刷新。
  • stderr 是非缓冲的,每次写入时都会立即刷新。

你可以搞乱python缓冲区或使stdout和stderr完全相同,但也许最简单的方法是尝试python -u ...使所有输出都是非缓冲的。这样,proc1的每次写入都应该以相同的顺序出现在proc2上。