一。提出问题,cmd.StderrPipe()和cmd.StdoutPipe()都无法获取后续输出
有时候在执行 exec.Command 的命令的时候,需要实时获取命令的输出,并不是一次性输出的,一般情况下都会用 cmd.StderrPipe() 以及 cmd.StdoutPipe() 来获取,比如你执行 ping 命令,但是,有些命令,只能接受第一次的输出,后续的无法接受到,拿这里的 tshark 命令为例
二,问题原因解释,可能是命令本身原因
这可能是由于 tshark 命令在进行数据捕获时会一直输出,直到用户中断命令或者捕获到结束符为止。因此,cmd.StderrPipe()
和cmd.StdoutPipe()
只能获取tshark
命令的初始输出,而无法获取后续输出。
要解决此问题,您可以通过在执行tshark命令时加入“-l”选项来强制tshark在输出每一行数据后刷新缓冲区,这样您就可以实时获取到输出。例如:
exec.Command("bash", "-c", "tshark -l -i 你的网卡名称 -n -T fields -e eth.src -e ip.src port 68")
三。代码例子(只不过在命令中 加了一个 -l 而已)
func useScan() {
go func() {
for {
cmd := exec.Command("bash", "-c", "tshark -l -i 你的网卡名称 -n -T fields -e eth.src -e ip.src port 68")
cmd.Run()
time.Sleep(time.Second * 2)
}
}()
cmd := exec.Command("bash", "-c", "tshark -l -i 你的网卡名称 -n -T fields -e eth.src -e ip.src port 68")
stderr, err := cmd.StderrPipe()
if err != nil {
return
}
stdout, err := cmd.StdoutPipe()
if err != nil {
return
}
if err := cmd.Start(); err != nil {
return
}
go func() {
scanner := bufio.NewScanner(stderr)
for scanner.Scan() {
line := scanner.Text()
log.Println("stderr:", line)
}
}()
go func() {
scanner := bufio.NewScanner(stdout)
for scanner.Scan() {
line := scanner.Text()
log.Println("stdout:", line)
}
}()
cmd.Wait()
}
这样,您就可以实时获取tshark命令的输出了。
四。结论及回顾
在执行命令中,要注意该命令是否只写入缓冲(该命令自己的缓冲),因为他不输出到我们程序的管道中,我们就无法获取到他的输出,其他命令同理,其他无法获取内容的,注意一下就行,看看哪个参数可以强制在输出每一行数据后刷新缓冲区,这样您就可以实时获取到输出
网友评论