继续浏览精彩内容
慕课网APP
程序员的梦工厂
打开
继续
感谢您的支持,我会继续努力的
赞赏金额会直接到老师账户
将二维码发送给自己后长按识别
微信支付
支付宝支付

Netty入门-《客户端-服务端》代码分析

wenhy
关注TA
已关注
手记 11
粉丝 15
获赞 106

服务端TimeServer:

package com.wenhy.netty;


import io.netty.bootstrap.ServerBootstrap;

import io.netty.channel.ChannelFuture;

import io.netty.channel.ChannelInitializer;

import io.netty.channel.ChannelOption;

import io.netty.channel.EventLoopGroup;

import io.netty.channel.nio.NioEventLoopGroup;

import io.netty.channel.socket.SocketChannel;

import io.netty.channel.socket.nio.NioServerSocketChannel;


public class TimeServer {

    public void bind(int port) throws Exception{

         //配置服务端的NIO线程组

         EventLoopGroup bossGroup = new NioEventLoopGroup();

         EventLoopGroup workerGroup = new NioEventLoopGroup();

         try{

         //netty用于启动NIO服务端的辅助启动类

         ServerBootstrap b = new ServerBootstrap();

         b.group(bossGroup, workerGroup)

            .channel(NioServerSocketChannel.class)

            .option(ChannelOption.SO_BACKLOG, 1024)

            .childHandler(new ChildChannelHandler());//绑定IO事件的处理类,记录日志、对消息进行编解码操作

         //绑定端口,同步等待成功

         ChannelFuture f = b.bind(port).sync();

        

         //等待服务端监听端口关闭

         f.channel().closeFuture().sync();

         } finally{

         //优雅退出,释放资源

         bossGroup.shutdownGracefully();

         workerGroup.shutdownGracefully();

         }

     }

     private class ChildChannelHandler extends ChannelInitializer<SocketChannel>{

         @Override

         protected void initChannel(SocketChannel arg0) throws Exception {

         arg0.pipeline().addLast(new TimeServerHandler());

     }

    

     }

     /**

     * @param args

     * @throws Exception 

     */

     public static void main(String[] args) throws Exception {

         int port = 8080;

         if(args != null && args.length >0 ){

         try {

         port = Integer.valueOf(args[0]);

         } catch (Exception e) {

         }

     }

      new TimeServer().bind(port);

     }

}

TimeServerHandler类:

package com.wenhy.netty;

import io.netty.buffer.ByteBuf;

import io.netty.buffer.Unpooled;

import io.netty.channel.ChannelHandlerContext;

import io.netty.channel.ChannelInboundHandlerAdapter;

public class TimeServerHandler extends ChannelInboundHandlerAdapter  {

@Override

public void channelRead(ChannelHandlerContext ctx, Object msg)

throws Exception {

//将请求的信息放到Netty的ByteBuf对象中,

ByteBuf buf = (ByteBuf) msg;

//通过ByteBuf的readableBytes方法可以获取缓冲区的可读字节数,根据可读字节数创建byte数组,通过ByteBuf的readbyte方法

//将缓冲区中的字节数复制到新建的数组中,

byte[] req = new byte[buf.readableBytes()];

buf.readBytes(req);

String boby = new String(req,"UTF-8");

System.out.println("The time server receive order : " + boby);

String currentTime = "QUERY TIME ORDER".equalsIgnoreCase(boby) ? 

new java.util.Date(System.currentTimeMillis()).toString() : "BAD ORDER";

ByteBuf resp = Unpooled.copiedBuffer(currentTime.getBytes());

ctx.write(resp);

}

@Override

public void channelReadComplete(ChannelHandlerContext ctx) throws Exception {

ctx.flush();

}

@Override

public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause)

throws Exception {

ctx.close();

}

}

客户端TimeClient:

package com.wenhy.netty;


import io.netty.bootstrap.Bootstrap;

import io.netty.channel.ChannelFuture;

import io.netty.channel.ChannelInitializer;

import io.netty.channel.ChannelOption;

import io.netty.channel.EventLoopGroup;

import io.netty.channel.nio.NioEventLoopGroup;

import io.netty.channel.socket.SocketChannel;

import io.netty.channel.socket.nio.NioSocketChannel;


public class TimeClient {

public void connect(int port,String host) throws Exception{

//配置客户端NIO线程组

EventLoopGroup group = new NioEventLoopGroup();

try {

Bootstrap b = new Bootstrap();

b.group(group).channel(NioSocketChannel.class)

.option(ChannelOption.TCP_NODELAY, true)

.handler(new ChannelInitializer<SocketChannel>() {


@Override

protected void initChannel(SocketChannel ch)

throws Exception {


ch.pipeline().addLast(new TimeClientHandler());

}

});

//发起异步连接操作

ChannelFuture f = b.connect(host,port).sync();

//等待客户端链路关闭

f.channel().closeFuture().sync();

} finally{

//优雅退出,释放NIO线程组资源

group.shutdownGracefully();

}

}

/**

* @param args

* @throws Exception 

*/

public static void main(String[] args) throws Exception {

int port = 8080;

if(args != null && args.length > 0){

try {

port = Integer.valueOf(args[0]);

} catch (Exception e) {

// TODO: handle exception

}

}

new TimeClient().connect(port, "127.0.0.1");

}

}

TimeClientHandler类:

package com.wenhy.netty;


import java.util.logging.Logger;


import io.netty.buffer.ByteBuf;

import io.netty.buffer.Unpooled;

import io.netty.channel.ChannelHandlerContext;

import io.netty.channel.ChannelInboundHandlerAdapter;


public class TimeClientHandler extends ChannelInboundHandlerAdapter{

private static final Logger logger = Logger.getLogger(TimeClientHandler.class.getName());

private final ByteBuf firstMessgse;

public TimeClientHandler(){

byte[] req = "QUERY TIME ORDER".getBytes();

firstMessgse = Unpooled.buffer(req.length);

firstMessgse.writeBytes(req);

}


/**

* 发送指令,当客户端与服务端建立连接后,Netty 的NIO线程会调用这个方法,发送查询时间的指令

*/

@Override

public void channelActive(ChannelHandlerContext ctx) throws Exception {


//调用这个方法将请求发送给服务端

ctx.writeAndFlush(firstMessgse);

}


/**

* 当服务端返回应答消息时,这个方法会被调用,从Netty的Buf中打印这个应答消息

*/

@Override

public void channelRead(ChannelHandlerContext ctx, Object msg)

throws Exception {

ByteBuf buf = (ByteBuf) msg;

byte[] req = new byte[buf.readableBytes()];

buf.readBytes(req);

String boby = new String(req,"UTF-8");

System.out.println("Now is : "+boby);

}


@Override

public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause)

throws Exception {

//释放资源

logger.warning("Unexpected exception from downstream : " + cause.getMessage());

ctx.close();

}


}


打开App,阅读手记
1人推荐
发表评论
随时随地看视频慕课网APP