Netty-入门demo

133 阅读1分钟

选择Netty的理由

  1. Java NIO编码比较复杂,要熟练掌握Selector、ServerSocketChannel、SocketChannel、ByteBuffer等。juejin.cn/post/744775… 可以参考笔者的这篇博文,实现一个简单demo级服务端和客户端通信需要大量的代码量。
  2. 需要对网络编程精通才能写出高质量的代码。
  3. 面对断连重连、网络闪断半包读写、失败缓存、网络拥塞和异常码流的处理等问题,NIO编程工作量和难度都非常大。
  4. JDK NIO的bug问题。

Netty NIO编程

使用Netty重构juejin.cn/post/744775… 代码

NettyServer

public class NettyServer {

    public static void main(String[] args) throws InterruptedException {
        NioEventLoopGroup bossGroup = new NioEventLoopGroup();
        NioEventLoopGroup workGroup = new NioEventLoopGroup();

        try {
            ServerBootstrap bootstrap = new ServerBootstrap();
            bootstrap.group(bossGroup, workGroup)
                    .channel(NioServerSocketChannel.class)
                    .childHandler(new ChildChannelHandler());
            ChannelFuture sync = bootstrap.bind(new InetSocketAddress(8080)).sync();
            sync.channel().closeFuture().sync();
        } finally {
            bossGroup.shutdownGracefully();
            workGroup.shutdownGracefully();
        }


    }

}

ChildChannelHandler

public class ChildChannelHandler extends ChannelInitializer<SocketChannel> {


    @Override
    protected void initChannel(SocketChannel ch) throws Exception {
        ch.pipeline().addLast(new NIOServerHandler());
    }
}

NIOServerHandler

public class NIOServerHandler extends SimpleChannelInboundHandler {


    @Override
    protected void channelRead0(ChannelHandlerContext ctx, Object msg) throws Exception {
        ByteBuf buf = (ByteBuf) msg;
        byte[] bytes = new byte[buf.readableBytes()];
        buf.readBytes(bytes);
        String s = new String(bytes, "UTF-8");
        System.out.println("服务端接收到客户端的消息:" + s);

        String resp = "hello client-----";
        ByteBuf reBuf = Unpooled.copiedBuffer(resp.getBytes());
        ctx.writeAndFlush(reBuf);
    }
}

NettyClient

public class NettyClient {

    public static void main(String[] args) {
        NioEventLoopGroup group = new NioEventLoopGroup();
        Bootstrap bootstrap = new Bootstrap();
        try {

            Bootstrap handler = bootstrap.group(group)
                    .channel(NioSocketChannel.class)
                    .handler(new ChannelInitializer<SocketChannel>() {

                        @Override
                        protected void initChannel(SocketChannel ch) {
                            ch.pipeline().addLast(new NioClientHandler());
                        }
                    });

            ChannelFuture sync = handler.connect(new InetSocketAddress("127.0.0.1", 8080)).sync();
            sync.channel().closeFuture().sync();

        } catch (InterruptedException e) {
            throw new RuntimeException(e);
        } finally {
            group.shutdownGracefully();
        }

    }
}

NioClientHandler

public class NioClientHandler extends ChannelInboundHandlerAdapter {


    @Override
    public void channelActive(ChannelHandlerContext ctx) throws Exception {
        String msg = "Hello server---------";
        ByteBuf buf = Unpooled.wrappedBuffer(msg.getBytes());

        ctx.writeAndFlush(buf);
    }


    @Override
    public void channelRead(ChannelHandlerContext ctx, Object msg) throws Exception {

        ByteBuf buffer = (ByteBuf) msg;
        byte[] bytes = new byte[buffer.readableBytes()];
        buffer.readBytes(bytes);
        String message = new String(bytes, "UTF-8");
        System.out.println("客户端接收到服务器的消息:" + message);
    }

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

image.png

image.png