8

Unit testing Stdout in Go

 2 years ago
source link: https://dev.to/lucassha/unit-testing-stdout-in-go-1jd
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.

Unit testing Stdout in Go

Sep 24

・2 min read

Figuring out how to unit test functions that print to the terminal can be something of a daunting task. Thankfully, it's actually pretty simple due to the magic of interfaces in Go!


This post is going to be short and sweet on how to test output by capturing it in a bytes.Buffer. Below, I have a function that accepts a string, prints out a statement, and then returns.

func SayHello(w io.Writer, name string) {
    fmt.Fprintf(w, "Hi, my name is %s\n", name)
}
Enter fullscreen modeExit fullscreen mode

The critical component of this function is the io.Writer interface variable being passed in. Because it is an interface, this function will accept any data type that implements the method Write(b []byte) (n int, err error).

This interface is implemented in the io package and the entire code can be seen here. Most importantly, here is the code below for the interface:

type Writer interface {
    Write(p []byte) (n int, err error)
}
Enter fullscreen modeExit fullscreen mode

So how do we print out this function to the terminal? We pass in os.Stdout, which has its own Write method! This can be seen here.

To print this out to our terminal, just add the following in the main() function.

func main() {
    SayHello(os.Stdout, "Shannon")
}
Enter fullscreen modeExit fullscreen mode

Now, we can move onto unit testing this specific function, which just outputs a name and greeting. In order to test it, we need to capture its output and then turn it into a string from a slice of bytes. To do this, we'll utilize the bytes.Buffer struct, which has a Write method to satisfy the Writer interface.

Here is the full test code in order to compare these:

func TestSayHello(t *testing.T) {
    tt := []struct {
        description string
        name        string
        expect      string
    }{
        {"Empty", "", "Hi, my name is \n"},
        {"Name1", "Shannon", "Hi, my name is Shannon\n"},
        {"Name2", "Shug", "Hi, my name is Shug\n"},
    }

    for _, tc := range tt {
        t.Run(tc.description, func(t *testing.T) {
            var output bytes.Buffer
            SayHello(&output, tc.name)
            if tc.expect != output.String() {
                t.Errorf("got %s but expected %s", output.String(), tc.expect)
            }
        })
    }
}
Enter fullscreen modeExit fullscreen mode

You'll notice that we are declaring a Buffer here: var output bytes.Buffer and then passing that buffer into the SayHello function. However, we are actually passing in the address of the buffer. This is due to the Buffer method for Write being a pointer receiver, which can be seen here.

And that's it! Run go test -v to see that all tests pass, and you have successfully captured the output of a command in order to unit test the output without actually returning the string value.


Recommend

  • 80

    转载请注明文章出处:https://tlanyan.me/php-output-vs-stdout/PHP包含了以php://开头的一系列输出输出流,如php://stdin, php://stdout等。今天查看代码...

  • 32

    环境: 操作系统:Windows 10 Go Version: go version go1.10.3 windows/amd64 示例代码: counts := make(map[string]int); os.Stdin.Chmod(os.ModeSetuid) input := bufio.NewScanner( os...

  • 47

    VarnishSpy Overview This is a simple client/server that will monitor the varnishncsa stdout for all the urls that are coming into varnish and connected clients will get a listing of the top 50 urls b...

  • 48
    • eli.thegreenplace.net 4 years ago
    • Cache

    Faking stdin and stdout in Go

    In this post I want to discuss faking (or redirecting ) standard input and output ( os.Stdin and os.Stdout ) in Go programs. This is often done in tests, but may also be useful in other scenarios. ...

  • 8
    • blog.mathieu-leplatre.info 3 years ago
    • Cache

    Python UTF-8 print fails when redirecting stdout

    Python UTF-8 print fails when redirecting stdoutPython UTF-8 print fails when redirecting stdout Wed 26 January 2011Consider the following piece of code: # -*- coding: utf-8 -*- print u"Վարդանաշեն" Runni...

  • 20
    • www.devdungeon.com 3 years ago
    • Cache

    Using stdin, stdout, and stderr in Python

    Introduction Among the popular operating systems, they have all standardized on using standard input, standard output, and standard error with file desciptors 0, 1, and 2 respectively. This allows you to pipe the inputs and outputs...

  • 12

    Introduction When you use print() in python the output goes to standard output or sys.stdout. You can directly call sys.stdout.write() instead of using print(), but you can also co...

  • 20
    • www.devdungeon.com 3 years ago
    • Cache

    STDIN, STDOUT, STDERR, Piping, and Redirecting

    Introduction Operating systems recognize a couple special file descriptor IDs: STDIN - 0 - Input usally coming in from keyboard. STDOUT - 1 - Output from the...

  • 11
    • note.qidong.name 3 years ago
    • Cache

    Bash打印中的stdout与stderr

    Bash打印中的stdout与stderr 2017-07-26 10:58:36 +08  字数:2134  标签: Bash 简介stdout与stderr

  • 5

    If you write code, write tests. – The Way of Testivus 目录 Table of Contents 背景 单元测试的重要性无需多言,但...

About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK