netty 简单的和浏览器交互实现信息回答

强烈推荐去弄懂Netty流程,再来写这个代码:

/**
 * 实现客户端发送一个请求,服务器返回信息
 * [主从线程模型]
 */
public class HelloServer {
    public static void main(String[] args) throws InterruptedException {

        //       主线程组 [接受客户端连接,但不做处理,和老板一样] 这个是主从模式的
        EventLoopGroup bosGroup = new NioEventLoopGroup();
        //从线程组 【老板线程组把任务丢给他,让手下去做任务 中介....】
        EventLoopGroup workerGroup = new NioEventLoopGroup();
        try {
            // netty服务器的创建, ServerBootstrap 是一个启动类
            ServerBootstrap serverBootstrap = new ServerBootstrap();
            serverBootstrap.group(bosGroup, workerGroup)     // 设置主从线程组
                    .channel(NioServerSocketChannel.class)          // 设置nio的双向通道
                    .childHandler(new HelloServerInitializer());                        // 子处理器,用于处理workerGroup
            // 启动server,并且设置8088为启动的端口号,同时启动方式为同步
            ChannelFuture channelFuture = serverBootstrap.bind(8088).sync();
            // 监听关闭的channel,设置为同步方式
            channelFuture.channel().closeFuture().sync();
        } finally {
            bosGroup.shutdownGracefully();
            workerGroup.shutdownGracefully();
        }

    }
}
HelloServer
/**
 * 初始化器 channel注册后 会执行里面相对应的初始化方法
 */
public class HelloServerInitializer extends ChannelInitializer<SocketChannel> {

    @Override
    protected void initChannel(SocketChannel socketChannel) throws Exception {
        //通过SocketChannel去获得对应的管道
        ChannelPipeline pipeline = socketChannel.pipeline();
        // 当请求到服务端,我们需要做解码,响应到客户端做编码
        pipeline.addLast("HttpServerCodec",new HttpServerCodec());
        // 添加自定义的助手类,返回 "hello netty"
        pipeline.addLast("customHandler",new CustomHandler());
    }
}
HelloServerInitializer
/**
 * @Description: 创建自定义助手类
 */
//SimpleChannelInboundHandler: 对于请求来讲,其实相当于[入站,入境]
public class CustomHandler extends SimpleChannelInboundHandler<HttpObject> {

    @Override
    protected void channelRead0(ChannelHandlerContext channelHandlerContext, HttpObject httpObject) throws Exception {
        // 通过上下文对象获取channel
        Channel channel = channelHandlerContext.channel();
        //判断请求是否Request请求
       if (httpObject instanceof HttpRequest){
           // 显示客户端的远程地址
           System.out.println(channel.remoteAddress());
           // 定义发送的数据消息
           ByteBuf content = Unpooled.copiedBuffer("Hello,Netty!", CharsetUtil.UTF_8);
           //构建一个http response
           DefaultFullHttpResponse response =
                   new DefaultFullHttpResponse(HttpVersion.HTTP_1_1,
                           HttpResponseStatus.OK,
                           content);
           // 为响应增加数据类型和长度(content.readableBytes是算出长度)
           response.headers().set(HttpHeaderNames.CONTENT_TYPE, "text/plain");
           response.headers().set(HttpHeaderNames.CONTENT_LENGTH, content.readableBytes());
           // 把响应刷到客户端 [写 和 刷新]
           channelHandlerContext.writeAndFlush(response);
       }
    }
//    下面是Channel的一下生命周期,我们重写即可


    @Override
    public void channelRegistered(ChannelHandlerContext ctx) throws Exception {
        System.out.println("Channel---注册");
        super.channelRegistered(ctx);
    }

    @Override
    public void channelUnregistered(ChannelHandlerContext ctx) throws Exception {
        System.out.println("Channel---移除");
        super.channelUnregistered(ctx);
    }

    @Override
    public void channelActive(ChannelHandlerContext ctx) throws Exception {
        System.out.println("Channel---活跃状态");
        super.channelActive(ctx);
    }

    @Override
    public void channelInactive(ChannelHandlerContext ctx) throws Exception {
        System.out.println("Channel---不活跃了");
        super.channelInactive(ctx);
    }

    @Override
    public void channelReadComplete(ChannelHandlerContext ctx) throws Exception {
        System.out.println("Channel---读取完毕");
        super.channelReadComplete(ctx);
    }

    @Override
    public void userEventTriggered(ChannelHandlerContext ctx, Object evt) throws Exception {
        System.out.println("Channel---用户事件触发");
        super.userEventTriggered(ctx, evt);
    }

    @Override
    public void channelWritabilityChanged(ChannelHandlerContext ctx) throws Exception {
        System.out.println("Channel---可写可改");
        super.channelWritabilityChanged(ctx);
    }

    @Override
    public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) throws Exception {
        System.out.println("Channel---捕获异常触发函数");
        super.exceptionCaught(ctx, cause);
    }

    @Override
    public void handlerAdded(ChannelHandlerContext ctx) throws Exception {
        System.out.println("Channel---助手类添加");
        super.handlerAdded(ctx);
    }

    @Override
    public void handlerRemoved(ChannelHandlerContext ctx) throws Exception {
        System.out.println("Channel---助手类移除");
        super.handlerRemoved(ctx);
    }
}
CustomHandler

运行:

 

 

 

 

因为...谷歌浏览器请求了2次,一次是正常,一次是图标icon,所以...

posted @ 2022-03-15 09:25  咸瑜  阅读(121)  评论(0编辑  收藏  举报