93

假设我想在 go 程序中运行 'ls',并将结果存储在字符串中。在 exec 和 os 包中似乎有一些 fork 进程的命令,但它们需要 stdout 等的文件参数。有没有办法将输出作为字符串?

4

8 回答 8

341

现在有一个更简单的方法:

package main

import (
    "fmt"
    "log"
    "os/exec"
)

func main() {
    out, err := exec.Command("date").Output()
    if err != nil {
        log.Fatal(err)
    }
    fmt.Printf("The date is %s\n", out)
}

out标准输出在哪里。它的格式是[]byte,但您可以通过以下方式轻松将其更改为字符串:

string(out)

您也可以使用CombinedOutput() 而不是Output()返回标准输出和标准错误。

执行命令

于 2013-04-04T15:41:01.607 回答
41

要将 stdout 和 stderr 都放入单独的字符串中,您可以像这样使用字节缓冲区:

cmd := exec.Command("date")
var outb, errb bytes.Buffer
cmd.Stdout = &outb
cmd.Stderr = &errb
err := cmd.Run()
if err != nil {
    log.Fatal(err)
}
fmt.Println("out:", outb.String(), "err:", errb.String())
于 2016-10-10T23:27:13.280 回答
7
cmd := exec.Command("ls", "-al")
output, _ := cmd.CombinedOutput()
fmt.Println(string(output))

或者

cmd := exec.Command(name, arg...)
stdout, err := cmd.StdoutPipe()
cmd.Stderr = cmd.Stdout
if err != nil {
    return err
}
if err = cmd.Start(); err != nil {
    return err
}
for {
    tmp := make([]byte, 1024)
    _, err := stdout.Read(tmp)
    fmt.Print(string(tmp))
    if err != nil {
        break
    }
}
于 2020-06-29T03:57:19.980 回答
6

我将它与最新版本的 GO (~1.11) 一起使用

// CmdExec Execute a command
func CmdExec(args ...string) (string, error) {

    baseCmd := args[0]
    cmdArgs := args[1:]

    log.Debugf("Exec: %v", args)

    cmd := exec.Command(baseCmd, cmdArgs...)
    out, err := cmd.Output()
    if err != nil {
        return "", err
    }

    return string(out), nil
}

// Usage:
// out, err := CmdExec("ls", "/home")
于 2019-02-08T04:57:31.450 回答
4

两种选择,具体取决于您喜欢的范例:

  1. os.ForkExec()
  2. 执行。运行()
于 2009-12-10T04:28:21.260 回答
3

使用exec.Run,将 Pipe 传递给标准输出。从它返回的管道中读取。

于 2009-12-09T21:44:37.580 回答
2

编辑:这个答案已经过时了。请参阅下面的 Fatih Arslan 的回答


通过将Pipe指定为标准输出(如果需要,还可以使用标准错误)来使用exec.Run 。它将返回 cmd,它在Stdout (和 Stderr)字段中包含一个os.File 。然后您可以使用例如ioutil.ReadAll来阅读它。

例子:

package main

import (
    "exec";
    "io/ioutil";
)

func main() {
    if cmd, e := exec.Run("/bin/ls", nil, nil, exec.DevNull, exec.Pipe, exec.MergeWithStdout); e == nil {
        b, _ := ioutil.ReadAll(cmd.Stdout)
        println("output: " + string(b))
    }
}
于 2009-12-11T06:13:12.240 回答
1

如果您想要string输出,strings.Builder则 [1] 比 bytes.Buffer

package main

import (
   "os/exec"
   "strings"
)

func main() {
   c, b := exec.Command("go", "version"), new(strings.Builder)
   c.Stdout = b
   c.Run()
   print(b.String())
}
  1. https://golang.org/pkg/bytes#Buffer.String
于 2021-04-04T21:29:02.663 回答