(转)lua protobuffer的实现
转自: http://www.voidcn.com/article/p-vmuovdgn-bam.html
(1)lua实现protobuf的简介
但遗憾的是,官网的probocol buffers并不支持lua,云风大侠做的pbc的项目,地址为:https://github.com/cloudwu/pbc/blob/master/binding/lua/README.md. 实现了protobuf对lua的支持。
主要步骤如下:
第一步: You specify how you want the information you're serializing to be structured by defining protocol buffer message types in .proto
files(定义.proto)
第二步: Once you've defined your messages, you run the protocol buffer compiler for your application's language on your .proto
file to generate data access classes.(编译.proto文件,生成.pb文件)
第三步: 使用pbc库提供的函数,实现protobuf.
(2)安装protobuf
下载地址:https://code.google.com/p/protobuf/
安装protobuf后,protobuf提供了protoc指令,可以编译.proto文件
#protobuf
cd $WORKDIR
tar xfz protobuf-2.4.1.tar.gz
cd protobuf-2.4.1
./configure || exit $?
make -j3 || exit $?
make install || exit $?
使用方法:protoc --descriptor_set_out test.pb test.proto
使用protoc -h 可以查看protoc的其他选项
把 多个proto 文件编译到一个.pb文件的方法: protoc --descriptor_set_out=$confdir/common.cmd.pb $protodir/*.proto
(3) 安装pbc
rm -rf pbc-master
tar xfz pbc-master.tar.gz
cd pbc-master
make || exit $?
cd binding/lua/ && make || exit $?
cp -rf protobuf.so $WORKDIR/lualib/
把编译生成的protobu.so文件放到LUA_PATH目录里面,当require "protobuf"的时候,可以找到这个文件。放在哪里不重要,重要的是让lua找到它。
除此之外,还有一步非常重要:
把 pbc/binding/lua/protobuf.lua 赋值到LUA_PATH目录中,当require "protobuf"的时候,可以找到这个文件。
http://www.cnblogs.com/ghost240/p/3253092.html 这篇文章中说,
LUA_PATH下,就可以调用protobuf中的库方法 是错的!在pbc/binding/lua下面编译出protobuf.so放在LUA_PATH下面,或者将protobuf.lua放在
(4)如何使用pbc
a: 定义一个common.proto文件
package Common;
message accountRegister
{
optional string accountid = 1;
optional string hashedpwd = 2;
}
b:编码common.proto,生成common.pb文件
protoc --descriptor_set_out=/common.pb common.proto
c: 初始化protobuf
require("protobuf") 特别需要注意
-- 生成的pb文件
local pbfile ="/path/to/common.pb"
local pbdesc = io.open(pbfile, "rb")
if not pbdesc then
echoError("failed to load protobuf description file:" .. pbfile)
return
end
local pbbuffer = pbdesc:read("*a")
protobuf.register(pbbuffer)
pbdesc:close()
d: 编码 protobuf.encode(ptype, msg)
ptype = 'Common.accountRegister' 千万不要忘了 Common前缀
msg = {accountid = '123', hashedpwd = '123456'} msg的声明的格式必须要和proto文件里声明的一样,否则编码不通过
e: 解码 protobuf.decode(pbtype, msgbuf) 返回msg 和err,具体的返回内容请参考pbc的文件