Parallel processing Netty并行处理器处理

Parallel processing Netty并行处理器处理,parallel-processing,netty,blocking,Parallel Processing,Netty,Blocking,按照其他地方的建议,我正试图在一个复杂的管道中并行化我的最终入站处理程序 public final class EchoServer { private EventLoopGroup group = new NioEventLoopGroup(); private UnorderedThreadPoolEventExecutor workers = new UnorderedThreadPoolEventExecutor(10); public void start(i

按照其他地方的建议,我正试图在一个复杂的管道中并行化我的最终入站处理程序

public final class EchoServer {
    private EventLoopGroup group = new NioEventLoopGroup();
    private UnorderedThreadPoolEventExecutor workers = new UnorderedThreadPoolEventExecutor(10);

    public void start(int port) throws InterruptedException {
        try {
            Bootstrap b = new Bootstrap();
            b.group(group).channel(NioDatagramChannel.class).option(ChannelOption.SO_BROADCAST, true)
                    .handler(new ChannelInitializer<NioDatagramChannel>() {
                        @Override
                        protected void initChannel(NioDatagramChannel channel) throws Exception {
                            channel.pipeline().addLast(workers, new SimpleChannelInboundHandler<DatagramPacket>() {
                                @Override
                                public void channelRead0(ChannelHandlerContext ctx, DatagramPacket packet) throws Exception {
                                    System.err.println(packet);
                                    // Simulated database delay that I have to wait to occur before repsonding
                                    Thread.sleep(1000);
                                    ctx.write(new DatagramPacket(Unpooled.copiedBuffer("goodbye", StandardCharsets.ISO_8859_1), packet.sender()));
                                }

                                @Override
                                public void channelReadComplete(ChannelHandlerContext ctx) {
                                    ctx.flush();
                                }

                                @Override
                                public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) {
                                    cause.printStackTrace();
                                }
                            });
                        }
                    });

            b.bind(port).sync().channel().closeFuture().await();
        } finally {
            group.shutdownGracefully();
        }
    }

    public void stop() {
        group.shutdownGracefully();
    }
}
公共最终类EchoServer{
private EventLoopGroup group=new NioEventLoopGroup();
私有UnorderedThreadPoolEventExecutor workers=新UnorderedThreadPoolEventExecutor(10);
public void start(int端口)抛出InterruptedException{
试一试{
引导b=新引导();
b、 组(组).channel(NioDatagramChannel.class).option(ChannelOption.SO_广播,true)
.handler(新的通道初始值设定项(){
@凌驾
受保护的void initChannel(NioDatagramChannel)引发异常{
channel.pipeline().addLast(工人,新的SimpleChannelInboundHandler()){
@凌驾
public void channelRead0(ChannelHandlerContext ctx,DatagramPacket数据包)引发异常{
系统错误打印项次(数据包);
//模拟数据库延迟,我必须等待发生在重新搜索之前
睡眠(1000);
write(新的DatagramPacket(unmooled.copiedBuffer(“再见”,StandardCharsets.ISO_8859_1),packet.sender());
}
@凌驾
公共无效channelReadComplete(ChannelHandlerContext ctx){
ctx.flush();
}
@凌驾
公共无效例外情况(ChannelHandlerContext ctx,可丢弃原因){
cause.printStackTrace();
}
});
}
});
b、 绑定(端口).sync().channel().closeFuture().await();
}最后{
group.ShutdownGracely();
}
}
公共停车场(){
group.ShutdownGracely();
}
}
作为测试,我有十个并发连接的客户端,我正在测量处理所有请求的执行时间。正如预期的那样,1秒钟的延迟和顺序执行只需要10秒钟。我试图将执行时间降低到2秒以下,以证明并行处理

据我所知,将处理程序添加到带有显式分配的执行器的管道中,应该使处理程序跨执行器中的线程并行工作


我没有看到性能的提高,而是发现当我添加并行处理时,我的客户机没有收到响应。线程睡眠用于模拟将传入数据写入数据库所需的潜在时间。我在这里做了一些明显错误的事情吗?

我解决了明显缺乏Netty支持的问题,即使用标准java并发机制并行执行最终的UDP处理

public final class EchoServer {
    private EventLoopGroup group = new NioEventLoopGroup();
    private ExecutorService executors = Executors.newFixedThreadPool(10);

    public void start(int port) throws InterruptedException {
        try {
            Bootstrap b = new Bootstrap();
            b.group(group).channel(NioDatagramChannel.class).handler(new ChannelInitializer<NioDatagramChannel>() {
                @Override
                protected void initChannel(NioDatagramChannel channel) throws Exception {
                    channel.pipeline().addLast(new SimpleChannelInboundHandler<DatagramPacket>() {
                        @Override
                        public void channelRead0(ChannelHandlerContext ctx, DatagramPacket packet) throws Exception {
                            CompletableFuture.runAsync(() -> {
                                System.err.println(packet);
                                try {
                                    Thread.sleep(1000);
                                } catch (InterruptedException e) {
                                    e.printStackTrace();
                                }
                                ctx.writeAndFlush(new DatagramPacket(Unpooled.copiedBuffer("goodbye", StandardCharsets.ISO_8859_1),
                                        packet.sender()));
                            }, executors);
                        }

                        @Override
                        public void channelReadComplete(ChannelHandlerContext ctx) {
                            ctx.flush();
                        }

                        @Override
                        public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) {
                            cause.printStackTrace();
                        }
                    });
                }
            });

            b.bind(port).sync().channel().closeFuture().await(); 
        } finally {
            group.shutdownGracefully();
        }
    }

    public void stop() {
        group.shutdownGracefully();
    }
}
公共最终类EchoServer{
private EventLoopGroup group=new NioEventLoopGroup();
私有ExecutorService executors=executors.newFixedThreadPool(10);
public void start(int端口)抛出InterruptedException{
试一试{
引导b=新引导();
b、 group(group).channel(NioDatagramChannel.class).handler(新的ChannelInitializer()){
@凌驾
受保护的void initChannel(NioDatagramChannel)引发异常{
channel.pipeline().addLast(新的SimpleChannelInboundHandler()){
@凌驾
public void channelRead0(ChannelHandlerContext ctx,DatagramPacket数据包)引发异常{
CompletableFuture.runAsync(()->{
系统错误打印项次(数据包);
试一试{
睡眠(1000);
}捕捉(中断异常e){
e、 printStackTrace();
}
ctx.writeAndFlush(新数据包(未冷却的复制缓冲区(“再见”,StandardCharsets.ISO_8859_1)),
packet.sender());
},遗嘱执行人);
}
@凌驾
公共无效channelReadComplete(ChannelHandlerContext ctx){
ctx.flush();
}
@凌驾
公共无效例外情况(ChannelHandlerContext ctx,可丢弃原因){
cause.printStackTrace();
}
});
}
});
b、 绑定(端口).sync().channel().closeFuture().await();
}最后{
group.ShutdownGracely();
}
}
公共停车场(){
group.ShutdownGracely();
}
}

显然,这是Netty在UDP通道方面的一个缺点。你能给我解释一下关于内蒂的一件事吗:如果我错了,请纠正我。因此,有一个事件循环(即解复用器)在等待请求,每当请求传入时,解复用器就会将其发送到处理程序管道。我的问题是,事件循环是否会阻止等待消息通过所有入站和出站处理程序?或者它只是发送并继续?不确定。我已经有一段时间没读这本书了。