[TOC]
go的工具比较丰富,为了保证代码的高质量可以多用下。
example
主要用于导入导GoDoc等工具生成的帮助文档中。它通过比较输出(stdout)和内部的(output)注释是否一致来判断是否成功。
func ExampleAdd() {
fmt.Pringln(add(1,2))
// Output:
// 3
}
如果没有output注释,该示例函数就不会被执行。另外,不能使用内置函数print/println,因为他们输出到stderr
go test
- 文件名以"_test.go"结尾。
- 测试函数以Test为名称前缀。
运行go test -v
执行单元测试。
运行go test ./...
测试当前包及所有子包。
常用测试参数
参数 | 说明 | 示例 |
---|---|---|
-args | 命令行参数 | |
-v | 输出详细信息 | |
-parallel | 并发执行,默认值为GOMAXPROCS | -parallel 2 |
-run | 指定测试函数,正则表达式 | -run “Add" |
-timeout | 全部测试累计时间超时将引发panic,默认值为10ms | -timeout 1m30s |
-count | 重复测试次数,默认值为1 |
benchmark
性能测试函数以Benchmark为名称前缀,同样保存在"*_test.go"文件中。
测试:
go test -bench .
如果希望仅执行性能测试函数,可以用run=NONE
忽略所有单元测试用例。
以下命令可以测试内存分配。
go test -bench . -benchmem -gcflags "-N -l"
也可增加代码报告内存使用情况b.ReportAllocs()
代码覆盖率
生成覆盖率报告
go test -cover
更详细的报告
- set: 是否执行
- count: 执行次数
- atomic: 执行次数,支持并发模式。
go test -cover -covermode count -coverprofile cover.out
查看报告
go tool cover -func=cover.out
web报告
go tool cover -html=cover.out
性能监控 Pprof
PProf 是用于可视化和分析性能分析数据的工具,PProf 以 profile.proto 读取分析样本的集合,并生成报告以可视化并帮助分析数据(支持文本和图形报告)。
而刚刚提到的 profile.proto 是一个 Protobuf v3 的描述文件,它描述了一组 callstack 和 symbolization 信息, 作用是统计分析的一组采样的调用栈,是很常见的 stacktrace 配置文件格式。
有哪几种采样方式
- runtime/pprof:采集程序(非 Server)的指定区块的运行数据进行分析。
- net/http/pprof:基于HTTP Server运行,并且可以采集运行时数据进行分析。
- go test:通过运行测试用例,并指定所需标识来进行采集。
支持什么使用模式
- Report generation:报告生成。
- Interactive terminal use:交互式终端使用。
- Web interface:Web 界面。
可以做什么
- CPU Profiling:CPU 分析,按照一定的频率采集所监听的应用程序 CPU(含寄存器)的使用情况,可确定应用程序在主动消耗 CPU 周期时花费时间的位置。
- Memory Profiling:内存分析,在应用程序进行堆分配时记录堆栈跟踪,用于监视当前和历史内存使用情况,以及检查内存泄漏。
- Block Profiling:阻塞分析,记录Goroutine阻塞等待同步(包括定时器通道)的位置,默认不开启,需要调用
runtime.SetBlockProfileRate
进行设置。 - Mutex Profiling:互斥锁分析,报告互斥锁的竞争情况,默认不开启,需要调用
runtime.SetMutexProfileFraction
进行设置。 - Goroutine Profiling:Goroutine 分析,可以对当前应用程序正在运行的 Goroutine 进行堆栈跟踪和分析。
其中像是 Goroutine Profiling 这项功能会在实际排查中会经常用到。
因为很多问题出现时的表象就是 Goroutine 暴增,而这时候我们要做的事情之一就是查看应用程序中的 Goroutine 正在做什么事情,因为什么阻塞了,然后再进行下一步。
介绍和使用
加入代码。
import (
_ "net/http/pprof"
)
示例保存了CPU和内存的采样数据:
go test -run NONE -bench . -memprofile mem.out -cpuprofile cpu.out net/http
参数 | 说明 | 示例 |
---|---|---|
-cpuprofile | 保存执行时间采样到指定文件 | -cpuprofile cpu.out |
-memprofile | 保存内存分配采样到指定文件 | -memprofile mem.out |
-memprofilerate | 内存分配采样起始值,默认为512KB | -memprofilerate 1 |
-blockprofile | 保存阻塞时间采样到指定文件 | -blockprofile block.out |
-blockprofilerate | 阻塞时间采样起始值,单位ns |
查看结果
go tool pprof http.test mem.out
- flat: 仅当前函数,不包括它调用的其他函数
- sum: 列表前几行所占百分比的总和。
- cum: 当前函数调用堆栈累计。
进一步查看。peek xxx
, 如peek malg
malg为函数名
也可以用list
命令输出源码行统计样式,一变更直观地定位。list malg
还可以输出svg图形。 web malg
在线采集
import (
_ "net/http/pprof"
)
浏览器直接访问 http://xxxx.com/debug/pprof 可以获取到概览情况。
/debug/pprof profiles: 21805 allocs 0 block 24 goroutine 21805 heap 0 mutex 23 threadcreate full goroutine stack dump
- allocs:查看过去所有内存分配的样本,访问路径为
$HOST/debug/pprof/allocs
。- block:查看导致阻塞同步的堆栈跟踪,访问路径为
$HOST/debug/pprof/block
。- cmdline:当前程序的命令行的完整调用路径。
- goroutine:查看当前所有运行的 goroutines 堆栈跟踪,访问路径为
$HOST/debug/pprof/goroutine
。- heap:查看活动对象的内存分配情况, 访问路径为
$HOST/debug/pprof/heap
。- mutex:查看导致互斥锁的竞争持有者的堆栈跟踪,访问路径为
$HOST/debug/pprof/mutex
。- profile:默认进行 30s 的 CPU Profiling,得到一个分析用的 profile 文件,访问路径为
$HOST/debug/pprof/profile
。- threadcreate:查看创建新OS线程的堆栈跟踪,访问路径为
$HOST/debug/pprof/threadcreate
。
如果你在对应的访问路径上新增 ?debug=1
的话,就可以直接在浏览器访问,没有debug参数就是下载。
然后再用go tool pprof 定位具体的项目。
go tool pprof http://xxxx.com/debug/pprof/heap?debug=1
通过交互式终端使用
譬如分析cpu使用率。
go tool pprof http://xxxx.com/debug/pprof/profile?seconds=60
如果是https的需要改为go tool pprof https+insecure://xxxx.com/debug/pprof/profile?seconds=60
(这个我试了是504错误)
具体的分析命令可执行pprof help
查看。介绍几个简单的。
top
- flat:函数自身的运行耗时。
- flat%:函数自身在 CPU 运行耗时总比例。
- sum%:函数自身累积使用 CPU 总比例。
- cum:函数自身及其调用函数的运行总耗时。
- cum%:函数自身及其调用函数的运行耗时总比例。
- Name:函数名。
list
查看源码。如
list encoding/json.checkValid
web
会生成svg文件。然后用浏览器打开就好了。
web界面
参考 https://mp.weixin.qq.com/s/9yLd7kkYzmbCriolhbvK_g
需要安装工具 brew install graphviz
火炬图的使用
参考 https://zhuanlan.zhihu.com/p/141640004
godoc
本地在线文档。需要先安装:
go get golang.org/x/tools/cmd/godoc
使用:
godoc -http=:6060