进程可以读取自己的“标准输出”流吗?

时间:2019-03-15 05:59:35

标签: multithreading go output outputstream

一个进程如何读取自己的输出流?我正在编写自动化测试,该自动化测试在与测试相同的过程中启动了几个应用程序子流程(应用程序)。因此,标准输出是测试输出和应用程序输出的混合。

我想在运行时读取输出流,如果看到应用程序中的错误,则测试失败。这可能/可行吗?如果是这样,我该怎么办?

注意:我知道我可以将应用程序作为独立的进程启动,然后读取其输出流。我现在的工作量很大。

还请注意,这不是How to test a function's output (stdout/stderr) in Go unit tests的伪装,尽管该票证是相似且有用的。另一个问题是关于捕获单个函数调用的输出。该票证是关于连续读取整个流的信息。正确答案也有所不同-它需要管道。

2 个答案:

答案 0 :(得分:2)

是的,您可以使用os.Pipe()然后自己处理:

tmp := os.Stdout
r, w, err := os.Pipe()
if err != nil {
    panic(err)
}
os.Stdout = w

或将os.Stdout转移到另一个文件或strings.Builder
这是详细的答案:
 In Go, how do I capture stdout of a function into a string?

答案 1 :(得分:0)

使用In Go, how do I capture stdout of a function into a string?os.Pipe的一种形式)对IPC中给出的答案进行了稍微修改:

  

Pipe返回一对已连接的文件;从r读取,返回写入w的字节。它返回文件和错误(如果有)。

由于os.Stdout*os.File,因此您可以将其替换为 any 文件。

 package main

 import (
    "bytes"
    "fmt"
    "io"
    "log"
    "os"
 )

 func main() {
    old := os.Stdout
    r, w, _ := os.Pipe() // TODO: handle error.
    os.Stdout = w

    // All stdout will be caputered from here on.

    fmt.Println("this will be caputered")

    // Access output and restore previous stdout.
    outc := make(chan string)

    go func() {
        var buf bytes.Buffer
        io.Copy(&buf, r) // TODO: handle error
        outc <- buf.String()
    }()

    w.Close()
    os.Stdout = old

    out := <-outc
    log.Printf("captured: %s", out)
 }