内容简介:首先通过监控工具查看到某个项目的机器内存在部署之后总是不断上涨,但是用户量并不多,很明显是内存泄漏的问题。项目中引入了以下代码,自然可以通过 pprof 工具进行分析。解决问题尝试了很多种方案,最后方案如下:
golang 内存泄漏的排查记录一
一、发现问题
首先通过监控 工具 查看到某个项目的机器内存在部署之后总是不断上涨,但是用户量并不多,很明显是内存泄漏的问题。
监控
二、如何解决
项目中引入了以下代码,自然可以通过 pprof 工具进行分析。
package main
import (
"net/http"
_"net/http/pprof"
)
func init() {
go func() {
http.ListenAndServe(":8000",nil)
}()
}
三、解决步骤
解决问题尝试了很多种方案,最后方案如下:
1、通过 pprof 工具获取内存相差较大的两个时间点 heap 数据。
curl localhost:8000/debug/pprof/heap > heap.base
等待一段时间,通过 htop 可以查看到内存又涨了很多,然后再采集内存情况
curl localhost:8000/debug/pprof/heap > heap.current
2、通过 go tool pprof 工具比较两个内存的情况,找到是什么对象多创建了
go tool pprof -http=:8080 -base heap.base heap.current
选择当前分配的对象(insue_objects):
option
得到如图所示:
pprof-heap-base
图中可以看出 withdraw_record.GetByUserId.FindAndCount() 在这段时间创建了 624110 个对象,于是怀疑是这里出了问题,于是去查看代码:
count, err = statement.Where("user_id = ? ", userId).FindAndCount(&records)
发现 statement 这个数据库 session 没有关闭,怀疑是因为没有关闭造成的问题
3、测试服问题复现
既然怀疑是这里的问题,然后就写了个 for 循环,不断地请求嫌疑接口,通过htop 发现,内存果然 蹭蹭蹭 网上涨,问题复现成功
4、将嫌疑代码修复了
修复就很简单了,加了一个 defer statement.Close()
5、部署修复后的代码到测试服务器验证
代码修复后,部署到测试服上,再用 for 循环去测,发现内存不再上涨,到此应该算是问题解决
6、查找项目中有没有类似代码并加以改正
四、注意点
1、不要在同一台机器一边跑项目,一边压测,否则两个程序都跑不满。
欢迎关注我们的微信公众号,每天学习 Go 知识
以上所述就是小编给大家介绍的《golang-pprof-排查内存泄漏(一)》,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对 码农网 的支持!
本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们。
Big C++中文版
霍斯特曼 / 姚爱红 / 电子工业 / 2007-3 / 85.00元
本书是一本关于C++的优秀教材,南圣何塞州立大学知名教授Horstmann编写。全书深入探讨了C++的知识,并着重强调了安全的标准模板库;本书较厚,但它可用做程序设计专业学生的教材(两学期)。全书在介绍基础知识后,作者论及了一些高级主题。书中面向对象的设计一章探讨了软件开发生命周期问题,给出了实现类关联的实用提示。其他高级主题包括模板,C++标准模板库,设计模式,GUI,关系数据库以及XML等。本......一起来看看 《Big C++中文版》 这本书的介绍吧!