企业为什么做网站系统,北京网站建设公司华网天下优惠,公司网站二维码生成器,东莞朝阳企讯网做的网站文章首发地址
TCP是一个“流”协议。所谓流#xff0c;就是没有界限的一长串二进制数据。拆包和粘包#xff1a;TCP作为传输层协议#xff0c;并不了解上层业务数据的具体含义#xff0c;它会根据TCP缓冲区的实际情况进行数据包的划分#xff0c;所以在业务上认为是一个完…文章首发地址
TCP是一个“流”协议。所谓流就是没有界限的一长串二进制数据。拆包和粘包TCP作为传输层协议并不了解上层业务数据的具体含义它会根据TCP缓冲区的实际情况进行数据包的划分所以在业务上认为是一个完整包的可能会被TCP拆分成多个包进行发送也有可能把多个小的包封装成一个大的数据包发送这就是所谓的TCP拆包和粘包问题。半包Netty在轮询读事件的时候每次从Channel中读取的数据不一定是一个完整的数据包这种情况就叫作半包。粘包Client往Server发送数据包时如果发送频繁很有可能会将多个数据包的数据都发送到通道中Server在读取的时候可能会读取到超过一个完整数据包的长度这种情况叫作粘包。
TCP 粘包/拆包问题说明
假设客户端分别发送了两个数据包 Dl 和 D2 给服务端由于服务端一次读取到的字节数是不确定的故可能存在以下 4 种情况。
服务端分两次读取到了两个独立的数据包分别是 D1 和 D2没有粘包和拆包服务端一次接收到了两个数据包 D1 和 D2 粘合在一起被称为 TCP 粘包服务端分两次读取到了两个数据包第一次读取到了完整的D1包和D2包的部分内容第二次读取到了D2包的剩余内容这被称为 TCP 拆包服务端分两次读取到了两个数据包第一次读取到了D1包的部分内容D1_1第二次读取到了D1包的剩余内容D1_2和D2包的整包。
TCP 粘包/拆包发生的原因
问题产生的原因有三个分别如下。
应用行序write 写入的字节大小大于套接日发送缓冲区大小进行 MSS 大小的 TCP 分段以太网帧的payload 大于MTU进行IP分片
粘包问题的解决策略
消息定长报文长度固定例如每个报文的长度固定为200字节如果不够空位补空格。报尾添加特殊分隔符例如每条报文结束都添加回车换行符如FTP或者指定特殊字符作为报文分隔符接收方通过特殊分隔符区分报文。将消息分为消息头和消息体消息头包含表示信息的总长度或者消息体长度的属性。更复杂的自定义应用层协议。 Netty对半包或者粘包的处理每个Handler都是和Channel唯一绑定的一个Handler只对应一个Channel所以Channel中的数据读取的时候经过解析如果不是一个完整的数据包则解析失败将这个数据包进行保存等下次解析时再和这个数据包进行组装解析直到解析到完整的数据包才会将数据包向下传递。
利用LineBasedFrameDecoder解决TCP粘包问题
LineBaseFrameDecoder的工作原理是它依次遍历ByteBuf中的可读下节判断否有“\n”或者\r\n, 如果有就以此位置为结束位置从可读索引到结束位置区间的字节就组成了一行。它是以换行符为结束标志的解码器支持携带结束符或者不携带结束符两种解码方式同时支持配置单行的最大长度。如果连续读取到最大长度后仍然没有发现换行符就会抛出异常同时忽略掉之前读到的异常码流。
StingDecoder的功能日常间单就是将接收到的对象转换成字符串然后继续调用后面的Handler。LineBasedFrameDecoder String Decoder组合就是按行切换的文本解码器它被设计用来支持 TCP 的粘包和拆包。
同时也支持其他的解码器以满足不同诉求。