BY Y!an - September 27, 2025

Go Practical Tips: Executing External Programs and Getting Streaming Output Like tail -f

Just tossing in a quick Go tip.

When using os/exec in Go to execute external commands, if the external command outputs continuously, how can we obtain its output in real-time and continuously?

It’s actually quite simple. You only need to create a pipe via StdoutPipe() to receive the standard output of the external command.

First, let’s prepare an external command program ./hello/main.cc:

#include "iostream"
#include <thread>

int main() {
    while (true) {
        auto now = std::chrono::system_clock::now();
        std::time_t now_c = std::chrono::system_clock::to_time_t(now);
        std::cout << "Current time is: " << std::ctime(&now_c) << std::flush;
        // sleep for a second
        std::this_thread::sleep_for(std::chrono::seconds(1));
    }
}

Then compile it with g++: g++ -o hello main.cc to get ./hello/hello. This program will output the current time every second.

Next, let’s start writing our Go program:

package main

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

func main() {
	cmd := exec.Command("./hello/hello")

	cmdStdout, err := cmd.StdoutPipe() // Create a pipe to receive the external command's standard output
	if err != nil {
		fmt.Println("Error creating StdoutPipe:", err)
		return
	}

	if err := cmd.Start(); err != nil {
		fmt.Println("Error starting command:", err)
		return
	}

	// Use a goroutine for non-blocking reception of the streaming output from the external command
	go func() {
		for {
			buf := make([]byte, 1024)
			n, err := cmdStdout.Read(buf)
			if err != nil {
				fmt.Println("Error reading from stdout:", err)
				break
			}

			if n == 0 {
				continue
			}

			// Trim trailing newline characters or '\0' (which is "\x00" in Go) as needed
			output := strings.TrimSuffix(string(buf[:n]), "\n")
			fmt.Println("Output:", output)
		}
	}()

	if err := cmd.Wait(); err != nil {
		fmt.Println("Error waiting for command:", err)
		return
	}
}

If you found this article helpful, you can buy me a coffee ↓