10.Netty框架-Netty编程模板(编解码和粘包拆包)

一、什么是分包/粘包

image.png

二、分包/粘包的原因

image.png

三、分包/粘包的解决方案

image.png

四、Netty内置的分包/粘包的处理器

1、通过制定的分割符来分割包:
LineBasedFrameDecoder: 通过\n 或者 \r\n, 进行分割包。
数据发送时:通过\n 或者 \r\n 切分包。
数据接收时:通过\n 或者 \r\n 切分包

2、自定义分隔符:
LineBasedFrameDecoder: 通过\n 或者 \r\n, 进行分割包,那么能否自定义分割符?
DelimiterBasedFrameDecoder


image.png

3、固定长度:
FixedLengthFrameDecoder


image.png

4、定义协议包含长度
4.1、通过ByteToMessageDecoder 实现自定义长度解析
···
public class IntegerHeaderFrameDecoder extends ByteToMessageDecoder {

 @Override
protected void decode( ChannelHandlerContext ctx, ByteBuf buf, List out) throws Exception {

  if (buf.readableBytes() < 4) {
     return;
  }

  buf.markReaderIndex();
  int length = buf.readInt();

  if (buf.readableBytes() < length) {
     buf.resetReaderIndex();
     return;
  }
 out.add(buf.readBytes(length));
}}···
 
 

4.2、通过ReplayingDecoder实现自定义长度解析
···
public class IntegerHeaderFrameDecoder extends ReplayingDecoder {

protected void decode(ChannelHandlerContext ctx,  ByteBuf buf) throws Exception {
  out.add(buf.readBytes(buf.readInt()));
}}···

ReplayingDecoder传递一个专门的ByteBuf实现,当缓冲区中没有足够的数据时,会抛出某种类型的一个Error。在上面的IntegerHeaderFrameDecoder,当调用buf.readInt()时,只能假定缓冲区有4个或更多的字节。如果,缓冲区中确实有4个字节,会返回你所期望的integer header。否则,会抛出这个Error。如果ReplayingDecoder捕获了这个Error,会重置缓冲区的readerindex到缓冲区的开始位置,并且当更多的数据到达缓冲区时,会再次调用decode()方法。

你可能感兴趣的:(10.Netty框架-Netty编程模板(编解码和粘包拆包))