特定目录结构的Golang应用如何运行测试并获取覆盖率?
直接在项目根目录执行不带参数的go test -cover时,Go 的测试命令默认仅扫描当前工作目录下的一级文件,不会递归遍历所有子目录的测试用例。
你项目根目录下不存在任何以_test.go结尾的测试文件,测试代码全部存放在test/pack子目录中,因此命令会直接返回[no test files]的提示,不会自动定位到深层目录的测试用例。
你之前测试将runner_test.go与runner.go放在同一目录时可以正常运行,本质是因为执行测试时直接命中了对应目录的测试文件,没有跨目录检索的环节。
在项目根目录(也就是存放go.mod的目录)下,可以根据需求选择以下命令运行测试、获取覆盖率:
- 运行项目下所有目录的测试用例,并输出基础覆盖率结果:
执行go test ./... -cover
其中./...是Go内置的通配符,会递归扫描项目内所有包含Go源码的目录,自动定位到test/pack下的测试文件执行,解决漏扫的问题。 - 仅运行指定测试包的用例,跳过无关目录的扫描:
执行go test ./test/pack -cover
直接指定测试文件所在的包路径,减少扫描范围、提升执行效率。
注意:默认的覆盖率统计逻辑只会计算测试文件所在包内的代码覆盖占比。
当测试文件和被测试源码位于同一目录时,二者同属一个包,不需要额外参数,默认就会对当前包计算覆盖率;但你当前的结构是测试和源码分属两个独立的包(pack和test/pack),如果不添加指定参数,统计的覆盖率会是test/pack目录下自身代码的覆盖情况,完全无法反映pack目录下业务代码的真实测试覆盖度,数值会和实际情况偏差极大。
要统计被测试源码包(即pack/runner.go所属的目录)的真实覆盖率,需要额外添加-coverpkg参数关联目标源码包,对应的完整命令为:go test ./test/pack -coverpkg=./pack -coverprofile=coverage.out
执行完成后可通过go tool cover -html=coverage.out命令,生成可视化的覆盖率明细报告。
内容的提问来源于stack exchange,提问作者Samyak

