java.lang.OutOfMemoryError:无法使用Netty客户端创建新的本机线程

java.lang.OutOfMemoryError:无法使用Netty客户端创建新的本机线程,java,out-of-memory,netty,Java,Out Of Memory,Netty,在933个线程之后,我们遇到以下错误 java.lang.OutOfMemoryError: unable to create new native thread at java.lang.Thread.start0(Native Method) at java.lang.Thread.start(Thread.java:714) at io.netty.util.concurrent.ThreadPerTaskExecutor.execute(ThreadPerTask

在933个线程之后,我们遇到以下错误

java.lang.OutOfMemoryError: unable to create new native thread
    at java.lang.Thread.start0(Native Method)
    at java.lang.Thread.start(Thread.java:714)
    at io.netty.util.concurrent.ThreadPerTaskExecutor.execute(ThreadPerTaskExecutor.java:32)
    at io.netty.util.internal.ThreadExecutorMap$1.execute(ThreadExecutorMap.java:57)
    at io.netty.util.concurrent.SingleThreadEventExecutor.doStartThread(SingleThreadEventExecutor.java:978)
    at io.netty.util.concurrent.SingleThreadEventExecutor.startThread(SingleThreadEventExecutor.java:947)
    at io.netty.util.concurrent.SingleThreadEventExecutor.execute(SingleThreadEventExecutor.java:830)
    at io.netty.util.concurrent.SingleThreadEventExecutor.execute(SingleThreadEventExecutor.java:818)
    at io.netty.channel.AbstractChannel$AbstractUnsafe.register(AbstractChannel.java:471)
    at io.netty.channel.SingleThreadEventLoop.register(SingleThreadEventLoop.java:87)
    at io.netty.channel.SingleThreadEventLoop.register(SingleThreadEventLoop.java:81)
    at io.netty.channel.MultithreadEventLoopGroup.register(MultithreadEventLoopGroup.java:86)
    at io.netty.bootstrap.AbstractBootstrap.initAndRegister(AbstractBootstrap.java:323)
    at io.netty.bootstrap.Bootstrap.doResolveAndConnect(Bootstrap.java:155)
    at io.netty.bootstrap.Bootstrap.connect(Bootstrap.java:116)
在netty中实现了http2客户端,用于向APN发送推送通知。 下面是客户端引导的代码。注意,我们没有在finally块中关闭通道。(channel.close().syncunterruptibly())。我们需要显式关闭通道还是调用singleNioEventLoopGroup.shutdownGracefully()释放资源?关闭通道是否会导致上述OOM错误

    public Integer sendNotification(String deviceToken, String alertPayLoad) throws Exception {
        EventLoopGroup singleNioEventLoopGroup = new NioEventLoopGroup();
        Channel channel = null;
        Integer response = 0;
        int streamId = -1;
        try {
            Bootstrap b = new Bootstrap();
            b.group(singleNioEventLoopGroup);
            b.channel(NioSocketChannel.class);
            b.option(ChannelOption.SO_KEEPALIVE, true);
            b.remoteAddress(host, port);
            b.handler(http2Client);
            channel = b.connect().syncUninterruptibly().channel();
            Http2SettingsHandler http2SettingsHandler = http2Client.getSettingsHandler();
            http2SettingsHandler.awaitSettings(TIME_OUT, TimeUnit.SECONDS);
            HttpHeaders httpHeaders = new DefaultHttpHeaders();
            httpHeaders.add(HttpConversionUtil.ExtensionHeaderNames.SCHEME.text(), HttpScheme.HTTPS);
            ByteBuf content = wrappedBuffer(alertPayLoad.getBytes(CharsetUtil.UTF_8));
            httpHeaders.add(HttpHeaderNames.CONTENT_LENGTH, String.valueOf(content.readableBytes()));
            FullHttpRequest request = new DefaultFullHttpRequest(HttpVersion.valueOf("HTTP/2.0"), HttpMethod.POST,
                new StringBuffer("https://").append(host).append("/3/device/").append(deviceToken).toString(), content, new DefaultHttpHeaders(), httpHeaders);
            Http2ResponseHandler responseHandler = http2Client.getResponseHandler();
            streamId = this.streamId.getAndAdd(2);
            responseHandler.put(streamId, channel.write(request), channel.newPromise());
            channel.flush();
            response = responseHandler.awaitResponses(TIME_OUT, TimeUnit.SECONDS);
        } finally {
            singleNioEventLoopGroup.shutdownGracefully();
        }
            return response;
    }

你刚才是不是把程序的全部源代码都放在了try-catch块中?总之,933个线程意味着1 gig的内存仅由线程使用,如果您不释放资源,则不需要DDOS攻击来关闭此服务器。您是否知道CPU仅为保持933个线程所需的工作量?仅仅因为你可以创建线程并不意味着你必须这样做。设置线程数的上限,让CPU平静地运行。