protobuf需要网络数据包头吗?
我正在使用 'protobuf' 进行使用 TCP 的 C/S 网络程序。
这是我对客户端的步骤:
1,将数据打包到“protobuf”中
2,获取包的大小(以字节为单位)并构造一个长度前缀帧
3,将帧+包写入套接字
,然后服务器:
1,读取长度-从socket中添加前缀帧并获取长度N
2,从socket读取N个字节并将数据填充到protobuf实例
3中,通过“key”从protobuf获取“value”,
我认为这似乎有点复杂,有吗某种为 protobuf 自动生成的长度前缀框架,那么我不需要自己构建一个。或者我还能做些什么来使代码更清晰?
I am using 'protobuf' for C/S network program using TCP.
here is my steps for client:
1, pack data into a 'protobuf'
2, get size in bytes of the pack and construct a length-prefix frame
3, write the frame+pack to socket
and then the server:
1, read Length-prefix frame from socket and get the length N
2, read N bytes from socket and fill the data into protobuf instance
3, get "value"s from protobuf by "key"s
it seems a little complicated I think, is there some kind of auto-generated length-prefix frame for protobuf, then I do not need construct one by myself. or anything else I can do to make code cleaner?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
使用 protobuf,假设您要在同一个管道中发送多条消息,那么:是的 - 您需要有一个长度作为前缀,否则它将想要读取到流的末尾。
protobuf 确实包含一些基本的 RPC 存根,但它们使用的 RPC 实现不属于 OSS 项目,因此不可用。不过,实现中列出了一些独立的 protobuf RPC 堆栈 。
就我个人而言,我倾向于假装数据序列是重复序列的一部分 - 即前缀为“字段 1,字符串”(又名
0a
),长度为“varint”编码。这意味着整个网络流都是有效的protobuf流。不过,这可能只是我的强迫症发作了。某些实现可能包含有助于解决此问题的功能。例如,protobuf-net(.NET 版本之一)具有
SerializeWithLengthPrefix
/DeserializeWithLengthPrefix
方法,该方法允许库为您执行此操作(同时提供一系列格式您的选择)。With protobuf, and assuming you are sending multiple messages down the same pipe, then: yes - you will need to have a length as a prefix, otherwise it will want to read to the end of the stream.
protobuf does include some basic RPC stubs, but the RPC implementation they use is not part of the OSS project, so that is not available. There are some standalone protobuf RPC stacks listed in the implementations though.
Personally, I tend to pretend that the sequence of data is part of a
repeated
sequence - i.e. prefix with "field 1, string" (aka0a
), and the length as "varint" encoded. This means that the entire network stream is a valid protobuf stream. That might just be my OCD kicking in, though.Some implementations may have features included to help with this. protobuf-net (one of the .NET versions) has
SerializeWithLengthPrefix
/DeserializeWithLengthPrefix
methods, for example, which lets the library do this for you (while offering a range of formats for your choosing).我不知道这是否适合您的作业,但我会研究已经为您想要支持的语言编写的“rpc 实现”之一。
https://github.com/protocolbuffers/protobuf/ blob/master/docs/third_party.md#rpc-implementations
例如,通过 Netty 内置的发送支持,我在 Java 中取得了很好的结果给定类型的
MessageLite
实例: http://docs.jboss.org/netty/3.2/guide/html/architecture.html#d0e1979(我确信你的长度标头可以完成这项工作好的,但是像 Netty 这样的框架将相对容易地添加对异步“双工”IO、SSL、身份验证等的支持)
HTH
I don't know if this is appropriate for your assignment, but I'd look into one of the 'rpc implementations' already written for the language(s) you want to support.
https://github.com/protocolbuffers/protobuf/blob/master/docs/third_party.md#rpc-implementations
e.g. I've had good results in Java with Netty's built-in support for sending
MessageLite
instances of a given type: http://docs.jboss.org/netty/3.2/guide/html/architecture.html#d0e1979(I'm sure your length header will do the job OK, but frameworks like Netty will add support for things like asynchronous 'duplex' IO, SSL, authentication, etc, with relative ease)
HTH