如何设计一个通信协议

如何设计一个通信协议

1. 网络层次

1.1具体层次以及封装

封装的协议结构一般是协议头+数据。

2. 网络通信存在问题

2.1 设计协议时,边界问题如何处理

场景以及问题:在TCP流式传输中,流式传输也就是一端只关心向管道发送数据,另外一边只要管道存在数据就接收数据。一个客户端发送N个100字节的消息,此时服务器接收数据可以每次读取100字节。但是当客服端每次发送的数据长度不一样的时候,比如发送200字节、500字节,此时如何对接收的数据进行一个拆分。

解决:

根据标识去拆分数据得到完整的一个消息。关键在于一个消息的起始边界的判定。

2.2 发送方和接收方如何通信

将客服端封装成应该person对象,然后发送对象以及对象的大小,也就是send(&person,sizeof(person))?存在什么问题?

问题就是如果数据是在堆上时,使用sizeof是有问题的。因为sizeof不能计算动态分配的内存。一般网络传输中都是使用序列化(将数据对象转换为二进制过程)和反序列化(将二进制恢复为数据对象过程)进行通信的。

3. 一个完整的通信协议应该包括以下组成部分:

1协议字段补充

如果需要处理不同业务功能时,可以在body里面封装不同的cmd(command),每一个不同的cmd标识不同的业务功能,比如login表示登录,regist表示注册。

appid:对外提供SDK服务时,用来识别不同的客服,比如英雄联盟的客户以及绝地求生的客户。

server_id:对应命令的分组。比如文件命令和网络命令,文件file命令下可以存在很多子命令,比如ls,tree等等。网路命令下也可以存在很多子命令,比如lsof,top等等。

command_id:具体的子命令,比如ls、tree等。

4. protobuf的使用

4.1 准备工作

下载安装protobuf工具,编译安装protobuf的cpp版本。

编写proto文件:也就是一个数据结构。包含通信协议的一些命令之类的详细结构。客服端和服务器需要同一份proto文件。主要这里不是说客服端和服务端在各自的git仓库建立一个proto文件,而是从一个git仓库拉取同一份proto文件(主要是为了后期维护,当一份修改时,另外一方可以实时知道)。

将proto文件生成对应的.cc和.h文件

4.2 protobuf经验总结

proto文件命名规则:比如IMLogin.pro,IM表示即时通信项目,Login登录相关的proto文件

proto命名空间:需要和文件命令空间对应。

引用文件:引用其他proto文件,需要加上命名空间package。(PDU:protocol data unit:通信数据单元。)

协议封装。

相关数据流

橙子卡激活教程 网上买的卡怎么激活?
勤策365

橙子卡激活教程 网上买的卡怎么激活?

⌚ 07-14 👁️‍🗨️ 4499
“皮皮虾我们走”到底是啥意思?
勤策365

“皮皮虾我们走”到底是啥意思?

⌚ 07-11 👁️‍🗨️ 8937
编程开发 -  MC百科社群 -   MC百科
勤策365

编程开发 - MC百科社群 - MC百科

⌚ 07-05 👁️‍🗨️ 1829