运行测试时如何丢弃打印输出

时间:2018-12-07 15:24:17

标签: go testing

使用Go 1.11我有一个在用户输入上方打印标签的功能。这很好并且可以工作,但是当我开始为此功能编写测试时,它将在运行测试时打印出此标签。

我也使用过log.Print,但是在测试文件中添加了以下内容

func init() {
  log.SetOutput(ioutil.Discard)
}

这将在运行测试时停止显示log.Print。那么,如何使它对任何fmt.Println都执行相同的操作?

更新

我以为我会发布我正在测试的功能以及如何设置,

func checkLoop(loopCount int) int {
  var input int
  var ok bool

  for !ok {
    fmt.Printf("Input %d  ::  ", loopCount)
    ok, input = takeInput()
  }

  return input
}

因此takeInput()仅使用fmt.Scan接受用户输入,并检查它是否在我想要的设定范围内。因此,它返回布尔值,如果为假,它将重新使用标签来检查它是什么输入数字。

3 个答案:

答案 0 :(得分:3)

要么您要在错误的水平上进行测试,要么您要进行错误的测试,让我解释一下。

  • 如果出于某种原因对您进行测试很有价值 您的函数会打印并接受用户输入, 然后继续进行端到端测试-也就是测试 它会打印出预期打印的内容,然后执行该操作,将其提交给罐头输入,然后验证它是否按照您期望的方式进行处理。

    我不知道您的代码,但是应该停止 使用fmt.P*函数系列-使用os.Std{in|out|err} 暗含并编写构成代码核心的函数,接受io.Readerio.Writer接口,并 从顶级代码中调用它们,并传递它们os.Stdinos.Stderr等。

    然后,在测试时,将很容易通过这些功能 同样满足上述接口要求的存根(或模拟)值。

    fmt程序包支持使用fmt.FP*函数系列进行格式化打印,其中F是一个历史文物,意为“文件”,并允许您通过实现{ {1}}。)

  • 另一种可能性是您所解释的看起来像 代码气味:与处理某些输入有关的功能 数据无处打印任何标签。

    这很可能是您应该拆分功能 至少分为两个部分:“外部”部分提示用户并读取数据,第二部分接受数据并进行处理。 然后,您测试第二个。

答案 1 :(得分:1)

fmt.Printf使用os.Stdout,因此您可以简单地进行以下操作:

os.Stdout = nil
fmt.Println("Hello Gopher!")

或更优雅:

os.Stdout,_ = os.Open(os.DevNull)
fmt.Println("Hello Gopher!")

希望获得帮助

答案 2 :(得分:1)

例如,

discard_test.go

package main

import (
    "fmt"
    "os"
    "syscall"
    "testing"
)

func printLabel(label string) {
    fmt.Println(label)
}

func TestDiscardLabel(t *testing.T) {
    defer func(stdout *os.File) {
        os.Stdout = stdout
    }(os.Stdout)
    os.Stdout = os.NewFile(uintptr(syscall.Stdin), os.DevNull)
    printLabel("Discard:")
}

func TestPrintLabel(t *testing.T) {
    printLabel("Print:")
}

输出:

$ go test discard_test.go -v
--- PASS: TestDiscardLabel (0.00s)
=== RUN   TestPrintLabel
Print:
--- PASS: TestPrintLabel (0.00s)
PASS
$