文章目录

  • 一、DelimiterBasedFrameDecoder
    • 服务端
      • 1、EchoServer
      • 2、EchoServerChannelHandler
      • 3、EchoServerHandler
    • 客户端
      • 1、EchoClient
      • 2、EchoClientChannelHandler
      • 3、EchoClientHandler
  • 二、FixedLengthFrameDecoder

TCP以流的方式进行数据传输,上层应用协议为了对消息进行区分,一般采用如下4种方式:

1.消息长度固定,累计读取到消息长度总和为定长Len的报文之后即认为是读取到了一个完整的消息。计数器归位,重新读取。
2. 将回车换行符作为消息结束符。
3. 将特殊的分隔符作为消息分隔符,回车换行符是他的一种。
4. 通过在消息头定义长度字段来标识消息总长度。

LineBasedframeDecoder属于第二种,今天我们要说的DelimiterBasedFrameDecoder和FixedLengthFrameDecoder属于第三种和第一种。DelimiterBasedFrameDecoder用来解决以特殊符号作为消息结束符的粘包问题,FixedLengthFrameDecoder用来解决定长消息的粘包问题。

一、DelimiterBasedFrameDecoder

服务端

1、EchoServer

/*** @author shuliangzhao* @Title: EchoServer* @ProjectName design-parent* @Description: TODO* @date 2019/8/21 20:53*/
public class EchoServer {public void start(int port) {EventLoopGroup bossGroup = new NioEventLoopGroup();EventLoopGroup workGroup = new NioEventLoopGroup();ServerBootstrap serverBootstrap = new ServerBootstrap().group(bossGroup,workGroup).channel(NioServerSocketChannel.class).childHandler(new EchoServerChannelHandler());try {ChannelFuture future = serverBootstrap.bind(port).sync();future.channel().closeFuture().sync();} catch (Exception e) {e.printStackTrace();} finally {bossGroup.shutdownGracefully();workGroup.shutdownGracefully();}}public static void main(String[] args) {new EchoServer().start(8080);}
}

2、EchoServerChannelHandler

/*** @author shuliangzhao* @Title: EchoServerChannelHandler* @ProjectName design-parent* @Description: TODO* @date 2019/8/21 20:59*/
public class EchoServerChannelHandler extends ChannelInitializer<SocketChannel> {protected void initChannel(SocketChannel socketChannel) throws Exception {ChannelPipeline pipeline = socketChannel.pipeline();ByteBuf byteBuf = Unpooled.copiedBuffer("\t".getBytes());pipeline.addLast(new DelimiterBasedFrameDecoder(1024,byteBuf));pipeline.addLast(new StringDecoder());pipeline.addLast(new StringEncoder());pipeline.addLast(new EchoServerHandler());}
}

3、EchoServerHandler

public class EchoServerHandler extends ChannelInboundHandlerAdapter {private int counter;@Overridepublic void channelRead(ChannelHandlerContext ctx, Object msg) throws Exception {String body = (String) msg;System.out.println("server reciver oder:" + body + ";this counter is:" + ++counter);}@Overridepublic void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) throws Exception {super.exceptionCaught(ctx, cause);}
}

客户端

1、EchoClient

public class EchoClient {public void start(String address,int port) {EventLoopGroup group = new NioEventLoopGroup();Bootstrap bootstrap = new Bootstrap();bootstrap.group(group).channel(NioSocketChannel.class).handler(new EchoClientChannelHandler());try {ChannelFuture future = bootstrap.connect(address,port).sync();future.channel().closeFuture().sync();} catch (Exception e) {e.printStackTrace();}finally {group.shutdownGracefully();}}public static void main(String[] args) {new EchoClient().start("127.0.0.1",8080);}
}

2、EchoClientChannelHandler

public class EchoClientChannelHandler extends ChannelInitializer<SocketChannel> {protected void initChannel(SocketChannel socketChannel) throws Exception {ChannelPipeline pipeline = socketChannel.pipeline();/** 这个地方的 必须和服务端对应上。否则无法正常解码和编码*/ByteBuf delimiter = Unpooled.copiedBuffer("\t".getBytes());pipeline.addLast(new DelimiterBasedFrameDecoder(1024,delimiter));pipeline.addLast( new StringDecoder());pipeline.addLast( new StringEncoder());// 客户端的逻辑pipeline.addLast( new EchoClientHandler());}
}

3、EchoClientHandler

public class EchoClientHandler extends ChannelInboundHandlerAdapter {private byte[] req;private int counter;public EchoClientHandler() {req = ("There are moments in life when you miss\t" +"someone so much that you just want to pick\t"    +"them from your dreams and hug them for real!\t"    +"Dream what you want to dream;go where you want\t"    +"to go be what you want to be,because you have only\t"   +"one life and one chance to do all the things you want to do\t").getBytes();}@Overridepublic void channelActive(ChannelHandlerContext ctx) throws Exception {ByteBuf message = Unpooled.buffer(req.length);message.writeBytes(req);ctx.writeAndFlush(message);}@Overridepublic void channelRead(ChannelHandlerContext ctx, Object msg) throws Exception {String body = (String) msg;System.out.println("client reciver is :" + body + "this is counter:" + ++counter);}@Overridepublic void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) throws Exception {ctx.close();}
}

运行结果:

这里我们添加DelimiterBasedFrameDecoder解码器并且手动指定消息分隔符为:”\t”。我们可以看一下DelimiterBasedFrameDecoder的构造方法:

public DelimiterBasedFrameDecoder(int maxFrameLength, boolean stripDelimiter, ByteBuf delimiter) {this(maxFrameLength, stripDelimiter, true, delimiter);
}

maxFrameLength:解码的帧的最大长度

stripDelimiter:解码时是否去掉分隔符

failFast:为true,当frame长度超过maxFrameLength时立即报TooLongFrameException异常,为false,读取完整个帧再报异常

delimiter:分隔符

二、FixedLengthFrameDecoder

FixedLengthFrameDecoder是固定长度解码器,它能够按照指定的长度对消息进行自动解码。
用法如下:
pipeline.addLast(new FixedLengthFrameDecoder(23));//参数为一次接受的数据长度。

Netty 框架学习(二):DelimiterBasedFrameDecoder和FixedLengthFrameDecoder相关推荐

  1. Netty 框架学习(二):Netty粘包和拆包

    文章目录 一.什么是粘包和拆包 二.粘包和拆包示例代码 1.TimeServerHandler 2.TimeClientHandler 三.使用Netty解决粘包和拆包 1.TimeServerHan ...

  2. java nio 客户端_Java网络编程:Netty框架学习(二)---Java NIO,实现简单的服务端客户端消息传输...

    概述 上篇中已经讲到Java中的NIO类库,Java中也称New IO,类库的目标就是要让Java支持非阻塞IO,基于这个原因,更多的人喜欢称Java NIO为非阻塞IO(Non-Block IO), ...

  3. PyTorch框架学习二十——模型微调(Finetune)

    PyTorch框架学习二十--模型微调(Finetune) 一.Transfer Learning:迁移学习 二.Model Finetune:模型的迁移学习 三.看个例子:用ResNet18预训练模 ...

  4. PyTorch框架学习二——基本数据结构(张量)

    PyTorch框架学习二--基本数据结构(张量) 一.什么是张量? 二.Tensor与Variable(PyTorch中) 1.Variable 2.Tensor 三.Tensor的创建 1.直接创建 ...

  5. Struts2框架学习(二) Action

    Struts2框架学习(二) Action Struts2框架中的Action类是一个单独的javabean对象.不像Struts1中还要去继承HttpServlet,耦合度减小了. 1,流程 拦截器 ...

  6. 《SpringBoot框架学习二之HTTP协议》

    <SpringBoot框架学习二之HTTP协议> 文章目录 <SpringBoot框架学习二之HTTP协议> 一.HTTP介绍 (1)概述 (2)HTTP版本协议 1.HTTP ...

  7. netty框架学习及springboot整合集成

    netty框架学习及springboot整合集成 1. Netty基本概念 2. Netty框架 2.1 Netty框架结构 2.1 Netty NIO 2.2 Reactor线程模型 3. Spri ...

  8. Netty 框架学习(一):初始netty

    文章目录 一.Netty简介 二.开发包获取 maven依赖 三.简单例子 服务端 客户端 一.Netty简介 官方定义为:"Netty 是一款异步的事件驱动的网络应用程序框架,支持快速地开 ...

  9. 【博学谷学习记录】超强总结,用心分享 | 架构师 Netty框架学习总结

    文章目录 前言 一.Netty · Netty简介 · Netty核心架构 · Netty中Reactor实现 1.工作流程 2.ChannelPipeline 和 ChannelHandler(开发 ...

最新文章

  1. 松下服务器分频器输出信号与,基础资料松下PANASONIC伺服驱动器MADHT1507E
  2. python代码规范链接
  3. 使用JMeter录制手机App脚本
  4. 引导界面(三)仿微信引导界面以及动画效果
  5. 【双非学历】历时1个月,18家公司,37轮面试,5个offer
  6. 最明的int和Integer的区别
  7. php如何检测图片背景是白色,javascript – 用PHP检测白色图像背景?
  8. nginx+tomcat 反向代理 负载均衡配置
  9. VS Code 全部快捷键一览表(巨TM全)
  10. Java 的日子屈指可数,这是真的吗?
  11. 漫画:什么是布隆算法
  12. java下拉树_参数模板中下拉树级联下拉数据集查询
  13. Callable介绍
  14. GraphQL实战经验和性能问题的解决方案
  15. 深度优先搜索(DFS)
  16. 发现了一个美图看看软件的一个bug
  17. 重写Java中equals和hashcode方法的一般规则
  18. 【机械仿真】基于matlab GUI凸轮设计与仿真【含Matlab源码 153期】
  19. linux系统调用使用方法,Linux系统的使用以及系统调用的开发方法OS.ppt
  20. [bzoj 4424]Cf19E Fairy

热门文章

  1. tensorflow计算图_简单谈谈Tensorflow的运行机制
  2. Java基础day7
  3. 系统架构师笔记(1)
  4. 趣学python3(2)-添加以数字文字形式使用下划线的功能,以提高可读性
  5. .net随笔-vb.net打开外部程序发送键盘信号(3)
  6. 牛客多校三 B Black and white
  7. 【机器学习】PyCaret!又一个神仙的自动机器学习库!
  8. 基于Python的特征自动化选择:两行代码完成特征工程
  9. 【科普】boy and girl,你是不是对算法工程师有误解
  10. 应届算法岗,选择巨头还是AI明星创业公司