这是我参与「第五届青训营 」伴学笔记创作活动的第 6 天
测试
go test 指定文件时默认执行文件内的所有测试用例。可以使用-run参数选择需要的测试用例单独执行。-v 可以使得输出的更详细
测试是避免事故的最后一道屏障
回归测试->集成测试->单元测试,从左到右,覆盖率逐层变大,成本却逐层降低
回归测试:比如刷一下抖音看看正不正常
集成测试:调用某个接口,自动化的看一下正不正确
单元测试:开发者对单独的函数或模块进行验证
这个命名有严格要求,必须以_test 命名,不然会报错
例子:
/test目录下
print_test.go
package test
import (
"testing"
)
func TestHelloTom(t *testing.T) {
output := HelloTom()
expectOutput := "Tom"
if output != expectOutput {
t.Errorf("Expected %s do not match actual %s", expectOutput, output)
}
}
print.go
package test
func HelloTom() string {
return "Jerry"
}
在编译器上找到print_test.go文件的TestHelloTom左边运行按键 或 在命令后用go test -v xxx_test.go xxx.go 这样可以两个文件同时编译,不会出现undefined的情况
换一个包,会报另一种形式的错误
如果正确
=== RUN Test_HelloTom
--- PASS: Test_HelloTom (0.00s)
PASS
或
ok command-line-arguments 0.561s
单元测试 - 覆盖率
如何衡量代码是否经过了足够的测试?
如何评价项目的测试水平?
如何评估项目是否达到了高水准测试等级?
看覆盖率
JudgeMent_Test文件夹下
judgement.go文件
package JudgeMent_Test
func JudgePassLine(score int16) bool {
if score >= 60 {
return true
}
return false
}
judgement_test.go文件
package JudgeMent_Test
import (
"github.com/stretchr/testify/assert"
"testing"
)
func TestJudgePassLineTrue(t *testing.T) {
isPass := JudgePassLine(70)
assert.Equal(t, true, isPass)
}
终端运行 go test . --cover
输出
ok test_project/test_project/Day2/JudgeMent_Test 0.324s coverage: 66.7% of statements
因为只运行了JudgePassLine函数的前两行,函数总共有三行有效代码。2/3=66.7%
现在要让它达到100%
func TestJudgePassLineTrue(t *testing.T) {
isPass := JudgePassLine(70)
assert.Equal(t, true, isPass)
}
func TestJudgePassLineFalse(t *testing.T) {
isPass := JudgePassLine(50)
assert.Equal(t, true, isPass)
}
终端运行 go test . --cover
一般覆盖率:50%-60%,较高覆盖率:80%+。
很难达到100覆盖率%
测试分支相互独立、全面覆盖。
测试单元粒度足够小,函数单一职责。
单元测试 - 文件处理
Mock函数,为一个函数/方法打桩,之后就算文件被修改删了也能运行
用一个函数A,替换函数B。
Patch(target,replacement interface{}) {
//将函数的地址替换成运行时地址
}
target是原函数,replacement是打桩的函数
Unpatch(target interface{}) bool {//测试结束后卸载桩
}
Mocktest文件
基准测试
优化代码,需要对当前代码分许
内置的测试框架提供了基准测试的能力
以 Benchmark 开头
benchmark文件夹
load_balance_selector.go
package benchmark
import (
"github.com/bytedance/gopkg/lang/fastrand"
"math/rand"
)
var Serverindex [10]int
func InitServerIndex() {
for i := 0; i < 10; i++ {
Serverindex[i] = i + 100
}
}
func SelectServerIndex() int {
return Serverindex[rand.Intn(10)]
}
func SelectFastServerIndex() int {
return Serverindex[fastrand.Intn(10)]
}
load_balance_selector_test.go
package benchmark
import "testing"
func BenchmarkSelect(b *testing.B) {
InitServerIndex()
b.ResetTimer() //删掉不属于我们测试的损耗
for i := 0; i < b.N; i++ { //串行的压力测试,也就是基准测试
SelectServerIndex()
}
}
func BenchmarkSelectServerIndexParallel(b *testing.B) {
InitServerIndex()
b.ResetTimer()
b.RunParallel(func(pb *testing.PB) { //并行的基准测试
for pb.Next() {
SelectServerIndex()
}
})
}
func BenchmarkSelectFastServerIndex(b *testing.B) {
InitServerIndex()
b.ResetTimer()
b.RunParallel(func(pb *testing.PB) {
for pb.Next() {
SelectFastServerIndex()
}
})
}
测试 go test -bench=.