Go:如何防止通过os.exec执行命令时管道阻塞?



在 Go 版本 1.14.2 中,下面是一些示例代码,它说明了通常建议的生成命令、通过 stdin 向其提供数据,然后捕获其 stdout 和 stderr 的方法。它使用管道,但如果 stdout 或 stderr 管道的缓冲区在进程完成之前已满,这可能会导致程序阻塞(此示例中省略了错误处理(......

func ExecExample(cmd *exec.Cmd, input *[]byte) {
stdout, err := cmd.StdoutPipe()
stderr, err := cmd.StderrPipe()
stdin, err := cmd.StdinPipe()
err = cmd.Start()
stdin.Write(*input)
stdin.Close()
stdoutBytes, err := ioutil.ReadAll(stdout)
stderrBytes, err := ioutil.ReadAll(stderr)
waitErr := cmd.Wait()
}

如何在 Go 中重组此示例代码,以便 stdout 和 stderr 管道永远不会阻塞?

另外,请注意,我正在寻找一种分别捕获标准输出和标准输出的方法。我不希望它们被合并。

提前谢谢你。

让 exec 包为您完成工作。

var stdout, stderr bytes.Buffer
cmd.Stdout = &stdout
cmd.Stderr = &stderr
cmd.Stdin = bytes.NewReader(*input)
err := cmd.Run()
stdoutBytes := stdout.Bytes()
stderrBytes := stderr.Bytes()

exec 包创建和管理将数据泵入子进程和从子进程泵送数据所需的 goroutine。

在操场上运行它。

在 goroutine中读取一个(或两个(流:

var stderrBytes []byte
go func() {
stderrBytes, _ = ioutil.ReadAll(stderr)
}()
err = cmd.Start()
stdoutBytes, err := ioutil.ReadAll(stdout)

最新更新