示例:Netty 处理 TCP数据分包协议

示例:Netty 处理 TCP数据分包协议

大家好,又见面了,我是全栈君,今天给大家准备了Idea注册码。

一个、Netty解决TCP协议的数据分包的想法


我们知道通过TCP协议发送接收数据时,假设数据过大。接收到的数据会是分包的。比方:

                                   
 +—–+—–+—–+
         发送数据是: | ABC | DEF | GHI |
                            +—–+—–+—–+
         而我们想接受到的数据是: | ABCDEFGHI |
                    

该怎样处理这样的情况呢?Netty提供了一个专门处理TCP协议数据的Handler:
LengthFieldBasedFrameDecoder ,它的原理是server端和client约定一个协议格式:数据包=协议长度+协议体

      ——————————–数据包——————————

   
 | 协议长度部分(接收数据长度) | 协议体部分(要接收的数据)|

举个样例,假如我们的TCPclient发送了10MB字节的数据,怎样让Nettyserver一次就接收到这10MB数据呢?那就须要client告诉服务端我发送的数据大小是多少,即在发送的数据中增加一个“数据包长度”就可以,上面提到的Handler就是用来和client约定这个协议格式的,它有几个參数,以下我介绍一下它的參数意义:
     
int
 maxFrameLength:定义接收数据包的最大长度,假设发送的数据包超过此值。则抛出异常;
     int
 lengthFieldOffset:长度属性部分的偏移值,0表示长度属性位于数据包头部。
     int
 
lengthFieldLength:长度属性的字节长度,假设设置为4,就是我们用4个字节存放数据包的长度;
     
int
 
lengthAdjustment:协议体长度调节值,修正信息长度,假设设置为4,那么解码时再向后推4个字节。
     
int
 
initialBytesToStrip:跳过字节数,如我们想跳过长度属性部分。

二、实例-client发送10MB字节的数据。Netty服务端一次接收到所有10MB数据

client:定义一个消息体,用头部四个字节存放数据包长度

public byte[] send(byte[] sendData) throws UnknownHostException, IOException {
		Socket socket = new Socket(serverIp, serverPort);
		OutputStream os = socket.getOutputStream();
		InputStream is = socket.getInputStream();
		byte resultArray[] = null;
		try {
			// 定义一个发送消息协议格式:|--header:4 byte--|--content:10MB--|
			// 获取一个4字节长度的协议体头
			byte[] dataLength = intToByteArray(4, sendData.length);
			// 和请求的数据组成一个请求数据包
			byte[] requestMessage = combineByteArray(dataLength, sendData);
			//发送数据-------------------------------
			os.write(requestMessage);
			os.flush();
			//接收数据-------------------------------
			resultArray = IOUtils.toByteArray(is);	
		} catch (Exception e) {
			e.printStackTrace();
		} finally {
			os.close();
			is.close();
			socket.close();
		}
		return resultArray;
	}
private static byte[] intToByteArray(int byteLength, int intValue) {
		return ByteBuffer.allocate(byteLength).putInt(intValue).array();
	}
private static byte[] combineByteArray(byte[] array1, byte[] array2) {
		byte[] combined = new byte[array1.length + array2.length];
		System.arraycopy(array1, 0, combined, 0, array1.length);
		System.arraycopy(array2, 0, combined, array1.length, array2.length);
		return combined;
	}

Netty服务端:定义一个LengthFieldBasedFrameDecoder(1024*1024*1024, 0, 4,0,4))。最大数据量是1GB,长度属性位于数据包头部,占4个字节,协议体调节值为0,跳过头部协议长度四个字节

@Override
			public void initChannel(SocketChannel ch) throws Exception {
				ChannelPipeline pipeline = ch.pipeline();

				pipeline.addLast("framedecoder",new LengthFieldBasedFrameDecoder(1024*1024*1024, 0, 4,0,4));
				pipeline.addLast(new TCPServiceHandler());// 处理业务Handler
				

			}

三、总结:client和服务端定义消息格式必须一致

版权声明:本文博客原创文章。博客,未经同意,不得转载。

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。

发布者:全栈程序员-站长,转载请注明出处:https://javaforall.net/117147.html原文链接:https://javaforall.net

赞 (0)
全栈程序员-站长的头像全栈程序员-站长


相关推荐

  • linux解压安装包rar_ubuntu rar文件解压

    linux解压安装包rar_ubuntu rar文件解压#wgethttps://www.rarlab.com/rar/rarlinux-x64-5.8.b4.tar.gz—>>下载包#ls-lrtrar/rar/order.htmrar/acknow.txtrar/readme.txtrar/default.sfxrar/license.txtrar/rarfiles.lstrar/…

    2022年10月21日
  • selenium自动化测试报告_selenium自动化测试断言

    selenium自动化测试报告_selenium自动化测试断言自动化测试——selenium(完结篇)文章目录自动化测试——selenium(完结篇)一、元素操作方法二、浏览器操作方法三、获取元素信息操作四、鼠标操作(需要实例化鼠标对象)4.1鼠标右键及双击4.2鼠标拖拽4.3鼠标悬停【重点】五、键盘操作(不需要实例化对象)☆六、元素等待七、下拉框(需要实例化下拉框)八、弹出框九、滚动条十、切换frame表单☆10.1连续切换frame十一、多窗口的切换☆十二、截图操作十三、验证码前言:看这篇帖子,最好要在知道定位八大元素的基础之上才能够比较熟练

    2022年10月1日
  • 自抗扰控制(ADRC)—— python 实战「建议收藏」

    自抗扰控制(ADRC)—— python 实战「建议收藏」本文利用跟踪微分器(TD)、扩张状态观测器(ESO)和非线性PID实现了受外扰的未知系统的控制,使得受控系统输出了期望信号。

    2022年5月18日
  • 安卓系统 第三方_第三方os

    安卓系统 第三方_第三方os安卓系统因其开源开放的特点,短短几年间就迅速占据了手机操作系统的大半的市场份额,Android平台提供给第三方开发商一个十分宽泛、自由的环境,不会受到各种条条框框的阻扰,因此也出现了许许多多的基于安卓

    2022年8月4日
  • html5设计礼品盒效果,十大包装创意设计网站「建议收藏」

    html5设计礼品盒效果,十大包装创意设计网站「建议收藏」有时您只需要一些启发。好吧,这是10个包装创意设计网站,这些网站充满了新颖的样品和具有创意的图文信息!花一些时间筛选它们,我们确信您会充满活力,可以重新包装或开始为您的产品选择正确的方向。没有比看看其他人为解决商品销售而进行的创新设计。这10个包装设计网站将使您的创意源源不断:1.www.thedieline.com还为包装设计缺乏灵感来源烦恼吗?现在,此网站为包装创意设计的访问量最大的网站之一…

    2022年10月28日
  • c语言编程 sort()什么意思,void sort在C语言中什么意思?「建议收藏」

    c语言编程 sort()什么意思,void sort在C语言中什么意思?「建议收藏」void是C语言中的一个关键字,其含义因其应用形式不同,一般分为两种:void和void*void的字面意思是“无类型”,void*则为“无类型指针”,void*可以指向任何类型的数据。void几乎只有“注释”和限制程序的作用,定义一个void变量没有意义,不妨试着定义:这行语句编译时会出错,提示“illegaluseoftype’void’”。不过,即使voida的编译不会出错,…

    2022年5月12日

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

关注全栈程序员社区公众号