Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

NioEvenLoopGroup应该使用全局共享单例,它不能完全关闭,频繁new和closeGracefully会造成内存耗尽! #35

Closed
canuran opened this issue Mar 25, 2020 · 2 comments

Comments

@canuran
Copy link

canuran commented Mar 25, 2020

因网络不通而频繁创建NioEvenLoopGroup导致内存耗尽,是我在项目中真实遇到的问题。
另外如果连接目标(包括失效的)过多也会导致内存耗尽,该问题在docker/k8s随机网络分配的环境下更明显 。
NioEvenLoopGroup应该使用单例模式,以下是我的解决方案:

定义自动检查的单例:

// 须使用getEventLoopGroup方法获取,勿直接使用
private static EventLoopGroup group = new NioEventLoopGroup();
private static ReentrantLock reentrantLock = new ReentrantLock();

public static EventLoopGroup getEventLoopGroup() {
    try {
        // 共享NioEventLoopGroup,因为是频繁要用的所以不要关闭group
        if (reentrantLock.tryLock(5, TimeUnit.SECONDS)) {
            // 如果关闭了则重新创建NioEventLoopGroup
            if (group == null || group.isShutdown() || group.isShuttingDown()) {
                group = new NioEventLoopGroup();
            }
            return group;
        } else {
            throw new IllegalStateException("Get the EventLoopGroup fail");
        }
    } catch (InterruptedException e) {
        Thread.currentThread().interrupt();
        throw new IllegalStateException("Get the EventLoopGroup fail");
    } finally {
        reentrantLock.unlock();
    }
}

使用时调用 getEventLoopGroup() 方法。

@xuxueli
Copy link
Owner

xuxueli commented Apr 15, 2020

你好,问题已修复并推送master分支,可以pull master体验下。将会跟随下个版本发布。

@xuxueli xuxueli closed this as completed Apr 15, 2020
@geercode
Copy link

xxl线程泄漏

雪里兄好,我在使用过程中发现有线程泄漏的问题,跟这位老兄的情况比较相似,但是我还没有看到很多的代码。我使用的xxl-job版本为2.0.2,xxl-rpc是1.4.0。由于开发环境没有xxl-admin,所以在发布时间一两天后,发现了有内存溢出,full gc过于频繁的问题,一开始发现byte[] object[] char[]过多,只定位到是netty出的问题,后用jprofiler查看内存,发现有线程数过多的情况,最终定位到是xxl造成的nettygroup线程过多造成的,截图如下:

xxl线程泄漏2

后沿着注册的Exception定位到是NettyHttpConnectClient#init方法中this.channel = bootstrap.connect(host, port).sync().channel();中sync()方法失败则造成nettyGroup的channel线程失去管理。由于我没有对netty深入研究过,这个地方是否应该在更高层级对资源进行限定,channel是否也应该避免用很多线程的粗放模式。原来提这个issue的老兄跟我说的比较像,是同一个问题吗,以及现在是否已经解决?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants