我试图了解如何将压缩(gzip)用于必须写入有效管道的进程。

如果未检测到管道,则封闭过程将出错,说明管道已损坏。据我所知,我是否具有以使用StdoutPipe?

对于此示例,我只是尝试对echo的输出进行gzip处理。

package main

import (
    "compress/gzip"
    //  "fmt"
    "io"
    "os"
    "os/exec"
)

func main() {
    f, _ := os.Create("/tmp/local_test.gz")

    cmd := exec.Command("echo", "my\nstrings\nare\nfancy")

    r, w := io.Pipe()
    gzw := gzip.NewWriter(w)

    out, _ := cmd.StdoutPipe()

    cmd.Start()

    go func() {
        // copy stdoutpipe to gz writer?
        io.Copy(w, out)
        gzw.Close()
        w.Close()
    }()

    // copy pipe to file?
    io.Copy(f, r)
}

该文件已写入,但不是gzip格式?
$ file /tmp/local_test.gz
/tmp/local_test.gz: data
$ gunzip /tmp/local_test.gz
gunzip: /tmp/local_test.gz: not in gzip format

最佳答案

您的管道无用地复杂,别忘了冲洗和关闭,请记住延后。

您只需要将f writer包装到gzip writer中,然后将stdout复制到writer中即可。

package main

import (
    "compress/gzip"
    "io"
    "os"
    "os/exec"
)

func main() {
    os.Remove("local_test.gz")
    f, _ := os.Create("local_test.gz")
    defer f.Close()

    cmd := exec.Command("echo", "my\nstrings\nare\nfancy")

    gzw := gzip.NewWriter(f)
    defer gzw.Close()
    defer gzw.Flush()

    out, _ := cmd.StdoutPipe()

    cmd.Start()

    io.Copy(gzw, out)

    // cmd.Wait() // to catch processing errors
}

结果检查
$ file local_test.gz
local_test.gz: gzip compressed data, original size 21
$ cat local_test.gz | gunzip -c
my
strings
are
fancy

关于go - 如何在使用stdoutpipe的命令中使用gzip进行压缩?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/58061182/

10-15 03:10