← 返回博客
go2026-09-12 22:37:322 分钟 · 454 0

Gin 性能调优:pprof 剖析与压测

用 net/http/pprof 给 Gin 接上运行时剖析,定位 CPU、内存、协程瓶颈,再用 vegeta 压测量化,做到先量再改。

#gin#性能调优#pprof

1. 先量化再改

凭感觉改性能是瞎调。先压测拿到基线 QPS 和延迟,用 pprof 抓到瓶颈在哪(CPU?分配?锁?),改完再压测对比。第 3 篇的 perf 思路同理。

2. 接 pprof

标准库 net/http/pprof 把剖析接口挂在独立端口,不影响业务路由:

import _ "net/http/pprof"

go func() {
    http.ListenAndServe("127.0.0.1:6060", nil) // 独立 debug 端口
}()

_ 导入自动注册 /debug/pprof/ 下的一系列路由。别挂到对外端口,只在调试环境开。

3. 抓 CPU profile

go tool pprof http://127.0.0.1:6060/debug/pprof/profile?seconds=30

采 30 秒 CPU 样本,进交互界面 top 看耗时函数,web 出火焰图。热点函数一目了然。

4. 抓内存和协程

go tool pprof http://127.0.0.1:6060/debug/pprof/heap      # 内存分配
go tool pprof http://127.0.0.1:6060/debug/pprof/goroutine # 协程数

内存涨不停看 heap,协程泄漏看 goroutine(没退出的协程堆积)。

5. 压测拿基线

echo "GET http://127.0.0.1:8080/articles/1" | vegeta attack -rate 1000 -duration 30s | vegeta report

rate 是每秒请求数,report 出延迟分布和成功率。先低压再加压,找到拐点 QPS。

6. 常见瓶颈

  • 锁竞争:sync.Mutex 粒度太大,pprof 的 mutex profile 能看到。
  • 频繁分配:热路径里反复 make/string 拼接,堆压力推高 GC。用 sync.Pool 或预分配。
  • N+1 查询:第 1 篇讲过的,一次请求打 N 次库,用 dataloader 或批量查。
  • 没设 context 超时:下游慢把连接/协程占满(第 3 篇)。

7. 上线清单

改性能前先压测基线,改完对比,别盲调。pprof 挂独立 debug 端口,生产按需开、不对外。CPU 看热点函数,内存看 heap,协程泄漏看 goroutine 数。定位到具体函数再改,改一处压一次。把 pprof 地址和压测脚本留进运维文档,下次有人能复现。

下一篇讲数据库进阶,连接池和读写分离是上线必踩的。

相关推荐

本文为原创文章,采用CC BY-NC-SA 4.0协议授权,转载请保留署名与原文链接。原文链接:https://www.wxbuluo.com/article/206