Stomp WebSocket出现ByteBuf未释放内存泄漏问题求助
Netty ByteBuf内存泄漏问题排查(Stomp + ActiveMQ Artemis)
问题描述
近期在基于Stomp和SockJS的系统中,出现Netty资源泄漏告警,具体日志如下:
05:49:52.704 [71] [tcp-client-loop-nio-2] ERROR io.netty.util.ResourceLeakDetector - LEAK: ByteBuf.release() was not called before it's garbage-collected. See https://netty.io/wiki/reference-counted-objects.html for more information. Recent access records: Created at: io.netty.buffer.PooledByteBufAllocator.newDirectBuffer(PooledByteBufAllocator.java:402) io.netty.buffer.AbstractByteBufAllocator.directBuffer(AbstractByteBufAllocator.java:187) io.netty.buffer.AbstractByteBufAllocator.directBuffer(AbstractByteBufAllocator.java:173) io.netty.buffer.AbstractByteBufAllocator.buffer(AbstractByteBufAllocator.java:107) org.springframework.messaging.tcp.reactor.ReactorNettyTcpConnection.send(ReactorNettyTcpConnection.java:60) org.springframework.messaging.simp.stomp.StompBrokerRelayMessageHandler$RelayConnectionHandler.forward(StompBrokerRelayMessageHandler.java:896) org.springframework.messaging.simp.stomp.StompBrokerRelayMessageHandler.handleMessageInternal(StompBrokerRelayMessageHandler.java:579) org.springframework.messaging.simp.broker.AbstractBrokerMessageHandler.handleMessage(AbstractBrokerMessageHandler.java:281) org.springframework.messaging.support.ExecutorSubscribableChannel$SendTask.run(ExecutorSubscribableChannel.java:144) io.opentracing.contrib.concurrent.TracedRunnable.run(TracedRunnable.java:30) java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1128) java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:628) java.base/java.lang.Thread.run(Thread.java:829) Netty.docs: Reference counted objects
系统使用ActiveMQ Artemis作为消息代理,以下是可能的泄漏诱因分析:
可能的诱因
- Spring框架版本bug:从栈轨迹看,泄漏发生在
ReactorNettyTcpConnection.send()方法。部分旧版本的Spring Messaging(如Spring Boot 2.x早期版本)在Stomp消息转发逻辑中,存在异常路径下ByteBuf未释放的漏洞,比如发送失败后未正确回收资源。 - 消息转发异常处理缺失:当
StompBrokerRelayMessageHandler向Artemis转发消息时,若出现网络中断、连接异常或Artemis返回错误帧,可能导致ByteBuf的生命周期未正常结束,遗漏release()调用。 - OpenTracing集成干扰:栈中出现
TracedRunnable,若OpenTracing的线程包装逻辑未正确传递资源释放上下文,可能导致异步任务中创建的ByteBuf无法被正常回收。 - Artemis协议适配问题:如果Artemis的Stomp协议处理存在异常(如响应帧不符合规范),会导致Spring Stomp客户端无法完成消息发送的完整流程,进而引发ByteBuf泄漏。
- 自定义逻辑资源管理不当:若存在自定义Stomp拦截器、消息转换器,修改消息内容时未正确处理ByteBuf的引用计数,也会导致资源泄漏。
排查建议
- 升级Spring Messaging/Spring Boot至最新稳定版本,确认是否有官方已修复的相关漏洞。
- 开启Netty paranoid级别的泄漏检测(添加JVM参数
-Dio.netty.leakDetection.level=PARANOID),获取更详细的泄漏轨迹,定位具体未释放的代码路径。 - 检查自定义的Stomp拦截器、消息处理器,确保没有持有ByteBuf引用而未调用
release()。 - 查看ActiveMQ Artemis的日志,排查是否存在连接异常、消息处理错误,确认是否由代理端问题触发客户端资源泄漏。
内容的提问来源于stack exchange,提问作者pacman
相关产品推荐
相关产品推荐

