网易首页 > 网易号 > 正文 申请入驻

同事用ThreadLocal记日志,7天后服务内存涨了47%我们才发现

0
分享至

一个Spring Boot服务,内存曲线像温水煮青蛙。不是暴涨,是每天涨一点。垃圾回收跑完,基线比昨天高一截。CPU正常,数据库正常,用户没投诉——这种bug最难抓。

作者Kavya的团队花了整整一周,才定位到罪魁祸首:一个看似无害的日志优化,用了ThreadLocal(线程本地存储)来存请求上下文。代码没报错,测试环境压测也扛得住。但生产环境跑了7天后,堆内存使用率从35%爬到82%,请求延迟从100ms飙到3秒。

这是Java工程师最熟悉的噩梦:内存泄漏从不敲门,它只在你放松警惕时,把服务慢慢勒死。

第一周:我们以为只是流量涨了

故事开始于一张"看起来正常"的监控图。Kavya在Medium上回忆,团队最初注意到内存缓慢上升时,第一反应是自我安慰——最近流量确实在涨,多占点内存不奇怪?

这个判断错得离谱。他们连续观察了三天,发现一个反常识的现象:凌晨流量低谷期,内存曲线依然向上。没有用户请求的时候,堆内存的基线(baseline)却在悄悄抬高。垃圾回收像在做无用功,每次扫完,留下的"干净空间"比上次更少。

到第5天,服务开始出现"亚健康"症状。不是宕机,是偶尔的卡顿。平时100ms的接口,冷不丁变成2秒、3秒。Kavya描述这种体验:"像开车时方向盘突然变沉,松手又好了,但你不敢再开快。"

团队终于认真起来。他们排除了数据库慢查询、第三方API超时、甚至怀疑过JVM(Java虚拟机)的GC算法参数。所有指标都正常,除了那条固执上扬的内存线。

ThreadLocal:被误用的"线程保险箱"

问题代码最终定位到一个日志工具类。同事为了简化代码,把用户ID、请求ID等上下文信息塞进了ThreadLocal。每个线程处理请求时存进去,打完日志再取出来——理论上很干净。

ThreadLocal的设计初衷是给每个线程独立的数据副本,避免锁竞争。但它在Java里有个致命搭档:线程池。

Spring Boot的Tomcat默认用线程池处理请求。一个线程不会用完即抛,而是被回收复用。这意味着:如果ThreadLocal里的数据没手动清理,它会跟着线程进入下一个请求,再下一个。Kavya的团队打了日志,却忘了在请求结束时调用remove()。

更隐蔽的是,他们存的不是简单字符串,是一个包含用户全量信息的上下文对象。每个泄漏的对象引用,都拖着一整棵树的数据。线程池越大,泄漏速度越慢——但也越难被发现。这就像往水库里滴墨水,池子大的时候,颜色变化根本看不出来。

作者没有透露具体数字,但描述了一个典型场景:服务重启后内存正常,7天后涨到危险水位。按Spring Boot默认的200线程池配置估算,每个泄漏对象若持有1MB数据,一周累积可达数百MB的"僵尸内存"。

为什么测试环境永远发现不了?

Kavya的文章戳中了一个行业痛点:这类bug在生产环境才显形。他们的CI/CD流水线跑了全套测试,包括压力测试。但压测通常持续几分钟到几小时,线程池来不及"养肥",内存泄漏的量级被淹没在正常波动里。

开发环境更惨。开发者本地重启服务的频率,可能比上厕所还高。ThreadLocal的问题需要"时间+线程复用"两个条件同时满足,而频繁重启直接把复用概率清零。

团队尝试过用Heap Dump(堆转储)分析,但初期抓到的快照里,泄漏对象被Tomcat的线程引用链埋得很深。Kavya写道:"你看到一堆org.apache.tomcat.util.threads.TaskThread,每个都挂着几MB数据,第一反应是Tomcat有问题,而不是自己的日志代码。"

最终破局的是一条Git提交记录。有人回忆起三个月前的一次"代码简化"重构,把原本显式传递的上下文参数,改成了ThreadLocal隐式存储。提交信息写着"减少方法签名冗余"——典型的技术债伪装成优化。

修复方案:比想象中更麻烦

找到根因只是开始。Kavya的团队面临一个尴尬选择:全局替换ThreadLocal方案,还是加remove()清理?

他们先试了后者。在Spring的拦截器里加finally块,确保请求结束调用ThreadLocal.remove()。测试通过,上线后内存曲线终于平了。但代码审查时,高级工程师提出质疑:如果某个异步线程忘了清理呢?如果未来有人新增入口点漏了拦截器呢?

ThreadLocal的清理是"人治",而人总会犯错。

团队最终回滚到显式传参方案。方法签名变长了,但数据流向一目了然。Kavya的反思很直接:"我们为了省几行代码,引入了隐式状态。这在并发编程里是最危险的trade-off(权衡)。"

文章结尾,作者提了一个未被回答的问题:如果当初选择用Java的ScopedValue(JDK 20引入的ThreadLocal替代方案),能否避免这场事故?ScopedValue设计为自动绑定到特定执行作用域,理论上无需手动清理。但Kavya的团队当时运行在JDK 17,升级成本又是另一个故事。

你的团队还在用ThreadLocal存请求上下文吗?最近一次代码审查,有人检查过remove()的调用位置吗——还是说,你们的服务也在某个角落,悄悄养着一池子泄漏的线程?

特别声明:以上内容(如有图片或视频亦包括在内)为自媒体平台“网易号”用户上传并发布,本平台仅提供信息存储服务。

Notice: The content above (including the pictures and videos if any) is uploaded and posted by a user of NetEase Hao, which is a social media platform and only provides information storage services.

相关推荐
热点推荐
曝巴萨确定免签31岁曼城队长 降薪6成+周薪12万镑 22岁红星或离队

曝巴萨确定免签31岁曼城队长 降薪6成+周薪12万镑 22岁红星或离队

我爱英超
2026-05-02 06:59:41
谈判破裂!央视回绝国际足联报价,中国球迷还能看到世界杯吗?

谈判破裂!央视回绝国际足联报价,中国球迷还能看到世界杯吗?

探史
2026-05-02 07:34:21
车载马桶,屎无前例的创新

车载马桶,屎无前例的创新

难得君
2026-05-01 18:05:01
25岁南开大学研究生李一帆确诊癌症,身高1米8长得帅,体重仅70斤

25岁南开大学研究生李一帆确诊癌症,身高1米8长得帅,体重仅70斤

阅微札记
2026-04-25 09:03:45
孙杨私生子风波升级,处处忍让的张豆豆,终究不再顾及所谓体面

孙杨私生子风波升级,处处忍让的张豆豆,终究不再顾及所谓体面

一盅情怀
2026-04-30 15:59:37
杨子离婚 3个月就和新欢产子,黄圣依17年青春喂了狗,体面尽失

杨子离婚 3个月就和新欢产子,黄圣依17年青春喂了狗,体面尽失

橙星文娱
2026-04-29 10:30:58
中央5台直播乒乓球时间:5月2日CCTV5、CCTV5+节目单,附国乒赛程

中央5台直播乒乓球时间:5月2日CCTV5、CCTV5+节目单,附国乒赛程

生活新鲜市
2026-05-02 11:55:19
苗原:山东泰山已经着手换掉马德鲁加

苗原:山东泰山已经着手换掉马德鲁加

懂球帝
2026-05-02 14:18:13
赴港一晚筹436万救患儿,李亚鹏全程弯腰致谢,背巨债干公益20年

赴港一晚筹436万救患儿,李亚鹏全程弯腰致谢,背巨债干公益20年

以茶带书
2026-05-01 18:12:05
中国代表:要防止朝鲜半岛生战生乱

中国代表:要防止朝鲜半岛生战生乱

新华社
2026-05-01 09:27:03
伦敦世乒赛爆出大冷,孙颖莎闺蜜输球!世界冠军惨败,赛后哽咽

伦敦世乒赛爆出大冷,孙颖莎闺蜜输球!世界冠军惨败,赛后哽咽

老王大话体育
2026-05-02 02:08:17
洛阳白马寺发布郑重声明:不少游客因通过非官方第三方渠道购买非法倒卖的预约门票,导致无法正常入寺,切勿轻信

洛阳白马寺发布郑重声明:不少游客因通过非官方第三方渠道购买非法倒卖的预约门票,导致无法正常入寺,切勿轻信

极目新闻
2026-04-29 18:10:47
唯一目标,领先6分!阿森纳拥有两个优势,曼城面临14天5场压力

唯一目标,领先6分!阿森纳拥有两个优势,曼城面临14天5场压力

嗨皮看球
2026-05-02 14:27:17
佛说:人若欠你,天必还你,即使再忙也要看完

佛说:人若欠你,天必还你,即使再忙也要看完

金沛的国学笔记
2026-05-02 11:42:14
宣布独立,中国未承认的有哪些?

宣布独立,中国未承认的有哪些?

地图帝
2026-05-02 12:07:52
追觅首谈造车:与小米同期启动,不必烧上千亿

追觅首谈造车:与小米同期启动,不必烧上千亿

虎嗅APP
2026-04-29 22:06:59
伊朗高级军事官员:伊美间再次爆发军事冲突可能性很大

伊朗高级军事官员:伊美间再次爆发军事冲突可能性很大

界面新闻
2026-05-02 14:34:33
7岁女孩独自走6公里上学,只有小狗相伴引发关注。

7岁女孩独自走6公里上学,只有小狗相伴引发关注。

一丝不苟的法律人
2026-04-27 14:58:35
心理学有个残忍发现:让别人对你产生敬畏感的,不是你的强势,不是你的反击,而是你骨子里的这两种“人性破绽”操控术

心理学有个残忍发现:让别人对你产生敬畏感的,不是你的强势,不是你的反击,而是你骨子里的这两种“人性破绽”操控术

心理观察局
2026-05-02 06:39:34
陕西男子3次报警,民警拒不派警,致两家四口被杀,法院咋判的?

陕西男子3次报警,民警拒不派警,致两家四口被杀,法院咋判的?

就一点
2026-04-29 17:28:35
2026-05-02 16:07:00
全栈遛狗员
全栈遛狗员
白天跟需求对线,晚上在小区遛狗。
2129文章数 55关注度
往期回顾 全部

科技要闻

AI热潮耗尽库存,Mac Mini起售调高200美元

头条要闻

以情报评估:美伊谈判或在下周初破裂 美或将重启战端

头条要闻

以情报评估:美伊谈判或在下周初破裂 美或将重启战端

体育要闻

休赛期总冠军,轮到休斯顿火箭

娱乐要闻

白百何罕晒大儿子 18岁元宝越来越帅

财经要闻

雷军很努力 小米还是跌破了30港元大关

汽车要闻

新纪录!零跑汽车4月交付达71387台

态度原创

手机
游戏
本地
健康
军事航空

手机要闻

俞浩再放狠话:追觅手机要与苹果、三星三分天下

《007》新作口碑爆了!年度最佳有力竞争者

本地新闻

用青花瓷的方式,打开西溪湿地

干细胞治烧烫伤面临这些“瓶颈”

军事要闻

特朗普:对伊战事结束 无限期延长停火

无障碍浏览 进入关怀版