上线三天 goroutine 数从两百涨到两万,抓一份 profile 看,前十几条栈全是 `goroutine 8831 [chan send, 8 minutes]:`,入口各不相同却卡在同一个发送点,重启能压回去,两天后又涨上来。第一次遇到会往复杂处想,其实漏掉的多是个小前提。

go tool pprof -http=:8080 goroutine.out
curl -s 'localhost:6060/debug/pprof/goroutine?debug=1'
go tool pprof http://127.0.0.1:6060/debug/pprof/goroutine

有协程往一个没人接收的 channel 发送,或者消费者提前 return 后再也没人读,发送方就永久阻塞在 chan send,运行时不会把它当成泄漏,数量只涨不降,只能靠重启清空。这一点先确认清楚,后面就不用反复试。

「goroutine 栈定位」这个问题文档写得含糊,实际行为以当前版本为准,别照旧版本的结论套。新版本先放一台机器上跑一天再全量,问题一般在这段时间暴露。

备份不是备了就行,恢复一次才算数,很多备份文件打开才发现是空的。

具体做法是,按栈里的函数名反查创建这个 channel 的那一行代码;确认消费方是不是在中途 return 之后再也没人读数据;发送端改成带取消信号和超时兜底的选择分支。

改完照着核一遍,重启后 goroutine 数稳定在两百上下,同一个栈不再堆积,两天后也没反弹。

作者 9823189