protobuf是一种跨语言协议,不同语言之间只需定义同一份proto文件,即可实现不同种类的语言的协议沟通。由于工作中使用c++解码较为麻烦,为了提升工作效率,想通过python达到快速解析pb数据的目的(系统为macOS Sierra)。
出自文章(https://segmentfault.com/a/1190000010098194)
python版本的protobuf安装
首先安装官方protobuf,通过执行protoc命令,可以将proto源文件编译成对应语言的数据结构文件和解析代码,如python对应的文件后缀名通常为.py和.pyc;安装官方,https://github.com/google/protobuf/releases,下载全量源码,然后解压、安装,然后确认安装是否成功。(此外可以通过 brew install protobuf 直接安装)
|
|
其次,安装对应的python protobuf模块,python引入该模块即可编写代码,实现pb文件的解析。安装python protobuf模块,首先安装pip,mac系统的python自带easy_install,因此直接输入命令:sudo easy_install pip;再通过pip来安装protobuf,命令:pip install protobuf;
遇到的问题:mac下python的six模块版本较低,且由于系统原因,无法被卸载安装新版,而pip在安装protobuf时需要,默认会下载安装较新版本的six模块,因此这里出现了冲突。通过参考该链接,https://github.com/pypa/pip/issues/3165,只需在使用pip安装python模块前,执行该命令即可:
|
|
使用python解析pb数据流程
这里使用c++对数据进行编码,并生成pb二进制文件,再通过python对pb二进制文件解码,得到c++输入的数据。使用c++写的client程序和python写的server服务器程序通信,在cleint端对数据编码,在server端对数据解码,通信方式采用socket,通信数据格式采用protobuf。
遇到的问题:当c++客户端-c++服务器,数据能正常编码和解析,而c++客户端-python服务器时,服务端python的recv函数接收的数据是null,无法正常接收。
解决方案:怀疑是python接收二进制数据问题,具体原因后续探究。因此把c++编码的protobuf数据再进行base64编码,将二进制proto数据变为字符串,当python服务端收到数据后,先进行base64解码,再对protobuf数据解码。
people.proto源文件:
|
|
切换到对应的proto源文件目录,执行命令,将产出两个文件people.pb.cc 和people.pb.h
|
|
切换到对应的proto源文件目录,执行以下命令,将产出文件people_pb2.pyc
|
|
c++客户端代码:
|
|
python2.7服务端程序:
|
|
服务端输出结果:
|
|