Go 1.17 发布七个月后,Go 1.18 正式发布了! Go 1.18 是一个包含大量新功能及新特性的版本,包括对语言本身做了有史以来最大的改变。其中最值得关注的新特性包括:范型,Fuzzing Test和Workspace。
接下来我会带大家一起来快速感受一下GO 1.18的新特性。
什么是模糊测试?
模糊测试是对Go原有测试包的一个扩充,它是一种自动化测试。通过随机生成输入数据来测试程序,用于尝试被程序员忽略的测试条件。甚至通过模糊测试可以找到的一些漏洞示例包括 SQL 注入、缓冲区溢出、拒绝服务和跨站点脚本攻击。
直接上例子
这里直接借用了Go官方文章中的例子(https://go.dev/doc/tutorial/fuzz)
package examples
import (
"testing"
"unicode/utf8"
)
// 被测试方法
func Reverse(s string) string {
b := []byte(s)
for i, j := 0, len(b)-1; i < len(b)/2; i, j = i+1, j-1 {
b[i], b[j] = b[j], b[i]
}
return string(b)
}
// Fuzz测试
func FuzzReverse(f *testing.F /* 注意:这里是testing.F */) {
/* 种子测试数据 */
testcases := []string{"Hello, world", " ", "!12345"}
for _, tc := range testcases {
f.Add(tc) // Use f.Add to provide a seed corpus
}
f.Fuzz(func(t *testing.T, orig string) {
rev := Reverse(orig)
doubleRev := Reverse(rev)
if orig != doubleRev {
t.Errorf("Before: %q, after: %q", orig, doubleRev)
}
if utf8.ValidString(orig) && !utf8.ValidString(rev) {
t.Errorf("Reverse produced invalid UTF-8 string %q", rev)
}
})
}
模糊测试程序编写要点:
-
测试函数以Fuzz开头, 参数为testing.F
-
f.Add 为添加种子测试数据,Fuzz测试将通过对种子测试数据进行随机变化而产生新的测试数据。(可以没有种子测试数据,直接生成随机测试数据)
-
f.Fuzz 的来运行fuzz测试,这个函数的参数是 func (t testing.T, … /*测数据类型列表*/) 。
运行测试程序:
通过命令行 go test -fuzz=. 来运行,这里与运行benchmark测试十分类似。
测试程序会一直运行下去,直到产生错误(触发测试失败的条件)或者运行时间超时,可以通过-fuzztime参数来指定超时时长。
导致测试失败的随机数据会被记录到 testdata/fuzz/FuzzReverse/路径下的文件中。并且该数据在我们再次运行测试时会被自动加入到种子测试数据中。
另,go test也可以运行Fuzz开头的测试函数,但是仅仅只会运行种子测试数据 (包括,我们上面提到的加入到种子数据中的失败case的数据)
注意事项
1. 目前模糊测试支持的随机测试数据类型:
-
string, []byte
-
int, int8, int16, int32/rune, int64
-
uint, uint8/byte, uint16, uint32, uint64
-
float32, float64
-
bool
2. 要保证Fuzz测试快速且具有确定性,以便测试引擎可以高效工作及轻松重现故障。
3.为了加快测试的速度,fuzz测试会通过并发的方式来执行,所以测试的实现中不应该依赖于任何共享状态。(测试执行的并发度/工作协程数可以通过 命令行参数-parallel来设置,默认值为$GOMAXPROCS)
思考
验证断言可以说是测试的灵魂。但由于测试数据是随机生成的,所以编写模糊测试时的验证断言并不像普通单元测试这样中容易写。
例如上面的例子中:
对于普通测试,如果输入数据是给定的,如:“hello”, 我们可以断言 Reverse (input) == “olleh”。而对于模糊测试,我们就无法这样简单的断言了,上面的测试中采用了 Reverse(Reverse(input)) == input 这样的巧妙方式。
很多时候,这样的测试验证断言是很难设计的,当然最基本的我们可以判断是否产生错误。
以上只是对该特性的简单介绍,更多内容大家可以参考官方文档学习。
文章评论