博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Netty官方示例
阅读量:5050 次
发布时间:2019-06-12

本文共 7697 字,大约阅读时间需要 25 分钟。

 

一、DEMO

官方并没有使用Hello World来作为一个例子,而是采用RFC的,这个协议定义了就是接收到请求后什么也不干。

第一步编写DiscardServerHandler类:

package io.netty.example.discard; import io.netty.buffer.ByteBuf;import io.netty.channel.ChannelHandlerContext;import io.netty.channel.ChannelInboundHandlerAdapter;import io.netty.util.ReferenceCountUtil;//ChannelInboundHandlerAdapter实现自ChannelInboundHandler//ChannelInboundHandler提供了不同的事件处理方法你可以重写public class DiscardServerHandler extends ChannelInboundHandlerAdapter {	/* 	 * @说明:该方法用于接收从客户端接收的信息	 * @时间:2017-4-2下午12:25:05	 * @see io.netty.channel.ChannelInboundHandlerAdapter#channelRead(io.netty.channel.ChannelHandlerContext, java.lang.Object)	 * @param ctx	 * @param msg	 * @throws Exception	 */	@Override	public void channelRead(ChannelHandlerContext ctx, Object msg)			throws Exception {		//Discard the received data silently		//ByteBuf是一个引用计数对象实现ReferenceCounted,他就是在有对象引用的时候计数+1,无的时候计数-1,当为0对象释放内存		ByteBuf in=(ByteBuf)msg;		try {			while(in.isReadable()){				System.out.println((char)in.readByte());				System.out.flush();			}		} finally {			ReferenceCountUtil.release(msg);		}	}		@Override	public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause)			throws Exception {		cause.printStackTrace();		ctx.close();	}}

  

第二步编写DiscardServer:

package io.netty.example.discard; 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 DiscardServer {	private int port;	public DiscardServer(int port){		this.port = port;	}		public void run() throws Exception{		//Group:群组,Loop:循环,Event:事件,这几个东西联在一起,相比大家也大概明白它的用途了。		//Netty内部都是通过线程在处理各种数据,EventLoopGroup就是用来管理调度他们的,注册Channel,管理他们的生命周期。		//NioEventLoopGroup是一个处理I/O操作的多线程事件循环		//bossGroup作为boss,接收传入连接		//因为bossGroup仅接收客户端连接,不做复杂的逻辑处理,为了尽可能减少资源的占用,取值越小越好		EventLoopGroup bossGroup=new NioEventLoopGroup(1);		//workerGroup作为worker,处理boss接收的连接的流量和将接收的连接注册进入这个worker		EventLoopGroup workerGroup=new NioEventLoopGroup();		try {			//ServerBootstrap负责建立服务端			//你可以直接使用Channel去建立服务端,但是大多数情况下你无需做这种乏味的事情			ServerBootstrap b=new ServerBootstrap();			b.group(bossGroup, workerGroup)			//指定使用NioServerSocketChannel产生一个Channel用来接收连接			.channel(NioServerSocketChannel.class)			//ChannelInitializer用于配置一个新的Channel			//用于向你的Channel当中添加ChannelInboundHandler的实现			.childHandler(new ChannelInitializer
() { public void initChannel(SocketChannel ch) throws Exception { //ChannelPipeline用于存放管理ChannelHandel //ChannelHandler用于处理请求响应的业务逻辑相关代码 ch.pipeline().addLast(new DiscardServerHandler()); }; }) //对Channel进行一些配置 //注意以下是socket的标准参数 //BACKLOG用于构造服务端套接字ServerSocket对象,标识当服务器请求处理线程全满时,用于临时存放已完成三次握手的请求的队列的最大长度。如果未设置或所设置的值小于1,Java将使用默认值50。 //Option是为了NioServerSocketChannel设置的,用来接收传入连接的 .option(ChannelOption.SO_BACKLOG, 128) //是否启用心跳保活机制。在双方TCP套接字建立连接后(即都进入ESTABLISHED状态)并且在两个小时左右上层没有任何数据传输的情况下,这套机制才会被激活。 //childOption是用来给父级ServerChannel之下的Channels设置参数的 .childOption(ChannelOption.SO_KEEPALIVE, true); // Bind and start to accept incoming connections. ChannelFuture f=b.bind(port).sync(); // Wait until the server socket is closed. // In this example, this does not happen, but you can do that to gracefully // shut down your server. //sync()会同步等待连接操作结果,用户线程将在此wait(),直到连接操作完成之后,线程被notify(),用户代码继续执行 //closeFuture()当Channel关闭时返回一个ChannelFuture,用于链路检测 f.channel().closeFuture().sync(); }finally{ //资源优雅释放 bossGroup.shutdownGracefully(); workerGroup.shutdownGracefully(); } } public static void main(String[] args) { int port=8088; try { new DiscardServer(port).run(); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } }}

 

二、ECHO协议的DEMO

协议,定义了客户端请求啥就返回啥

第一步编写EchoServerHandler:

package io.netty.example.echo; import io.netty.channel.ChannelHandlerContext;import io.netty.channel.ChannelInboundHandlerAdapter; public class EchoServerHandler extends ChannelInboundHandlerAdapter {	/* 	 * @说明:该方法用于接收从客户端接收的信息	 * @时间:2017-4-8下午12:08:51	 * @see io.netty.channel.ChannelInboundHandlerAdapter#channelRead(io.netty.channel.ChannelHandlerContext, java.lang.Object)	 * @param ctx	 * @param msg	 * @throws Exception	 */	@Override	public void channelRead(ChannelHandlerContext ctx, Object msg)			throws Exception {		//ChannelHandlerContext提供各种不同的操作用于触发不同的I/O时间和操作		//调用write方法来逐字返回接收到的信息		//这里我们不需要在DISCARD例子当中那样调用释放,因为Netty会在写的时候自动释放		//只调用write是不会释放的,它会缓存,直到调用flush		ctx.write(msg);		ctx.flush();		//你可以直接使用writeAndFlush(msg)		//ctx.writeAndFlush(msg);	}		@Override	public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause)			throws Exception {		cause.printStackTrace();		ctx.close();	}}

 

第二步编写EchoServer:

package io.netty.example.echo; 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 EchoServer {	private int port;	public EchoServer(int port){		this.port = port;	}		public void run() throws Exception{		//NioEventLoopGroup是一个处理I/O操作的多线程事件循环		//bossGroup作为boss,接收传入连接		//bossGroup只负责接收客户端的连接,不做复杂操作,为了减少资源占用,取值越小越好		//Group:群组,Loop:循环,Event:事件,这几个东西联在一起,相比大家也大概明白它的用途了。		//Netty内部都是通过线程在处理各种数据,EventLoopGroup就是用来管理调度他们的,注册Channel,管理他们的生命周期。		EventLoopGroup bossGroup=new NioEventLoopGroup(1);		//workerGroup作为worker,处理boss接收的连接的流量和将接收的连接注册进入这个worker		EventLoopGroup workerGroup=new NioEventLoopGroup();		try {			//ServerBootstrap负责建立服务端			//你可以直接使用Channel去建立服务端,但是大多数情况下你无需做这种乏味的事情			ServerBootstrap b=new ServerBootstrap();			b.group(bossGroup, workerGroup)			//指定使用NioServerSocketChannel产生一个Channel用来接收连接			.channel(NioServerSocketChannel.class)			//ChannelInitializer用于配置一个新的Channel			//用于向你的Channel当中添加ChannelInboundHandler的实现			.childHandler(new ChannelInitializer
() { public void initChannel(SocketChannel ch) throws Exception { ch.pipeline().addLast(new EchoServerHandler()); }; }) //对Channel进行一些配置 //注意以下是socket的标准参数 //BACKLOG用于构造服务端套接字ServerSocket对象,标识当服务器请求处理线程全满时,用于临时存放已完成三次握手的请求的队列的最大长度。如果未设置或所设置的值小于1,Java将使用默认值50。 //Option是为了NioServerSocketChannel设置的,用来接收传入连接的 .option(ChannelOption.SO_BACKLOG, 128) //是否启用心跳保活机制。在双方TCP套接字建立连接后(即都进入ESTABLISHED状态)并且在两个小时左右上层没有任何数据传输的情况下,这套机制才会被激活。 //childOption是用来给父级ServerChannel之下的Channels设置参数的 .childOption(ChannelOption.SO_KEEPALIVE, true); // Bind and start to accept incoming connections. ChannelFuture f=b.bind(port).sync(); // Wait until the server socket is closed. // In this example, this does not happen, but you can do that to gracefully // shut down your server. //sync()会同步等待连接操作结果,用户线程将在此wait(),直到连接操作完成之后,线程被notify(),用户代码继续执行 //closeFuture()当Channel关闭时返回一个ChannelFuture,用于链路检测 f.channel().closeFuture().sync(); }finally{ //资源优雅释放 bossGroup.shutdownGracefully(); workerGroup.shutdownGracefully(); } } public static void main(String[] args) { int port=8088; try { new EchoServer(port).run(); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } }}

  

三、依赖:

io.netty
netty-all
4.1.6.Final

 

 

 

 

 

 

 

 

 

来源:https://blog.csdn.net/wocjy/article/details/78661464

转载于:https://www.cnblogs.com/panchanggui/p/9829483.html

你可能感兴趣的文章
oracle中所有存在不存在的用户都可以使用dba连接到数据库
查看>>
函数式编程思想
查看>>
java安全沙箱(二)之.class文件检验器
查看>>
Oracle学习之简单查询
查看>>
log4j配置
查看>>
linux 配置SAN存储-IPSAN
查看>>
双链表
查看>>
java学习笔记之String类
查看>>
pymysql操作mysql
查看>>
Linux服务器删除乱码文件/文件夹的方法
查看>>
牛腩记账本core版本源码
查看>>
Word Break II
查看>>
UVA 11082 Matrix Decompressing 矩阵解压(最大流,经典)
查看>>
无线通讯
查看>>
Mongodb Manual阅读笔记:CH9 Sharding
查看>>
AX2009使用NPOI导出EXCEL2007
查看>>
如何删除NSDictionary或NSArray中的NSNull
查看>>
ueditor 结合easyui使用
查看>>
thymeleaf学习笔记
查看>>
进程(第一部分)
查看>>