下面用一个例子来说明如何在java中使用Protocol Buffer。
首先我们需要去Google的网站上下载Protocol Buffer的编译器:https://developers.google.com/protocol-buffers/docs/downloads,这里注意需要科学上网。
在Java中使用ProtocolBuffer的步骤大致分为下面这几点:
(1)编写.proto文件,定义消息类型
(2)使用ProtocolBuffer的编译器,将.proto文件编译成对应的java文件
(3)在Java代码中使用上一步编译好的java文件
如何编写.proto文件呢,看下面一个例子:
package com.demo.msg; option java_outer_classname = "PersonBean"; message Person { required string name = 1; required int32 age = 2; optional string gender = 3; }上面的代码可以保存到一个Person.proto文件中,其中package指定了包名,和java中的包名类似,option java_outer_classname = "PersonBean";这句指定了编译器在编译.proto文件时,输出的java类的类名,接着使用message定义了一个名为Person的消息,里面包含3个成员变量,其中用required修饰的变量代表必须的,optional修饰的变量代表是可选的,这里定义消息的形式跟java中定义类非常相似。下面需要用ProtocolBuffer的编译器来编译上面的消息,我们从google的网站上下载下来的是一个protoc.exe文件,将该文件跟上面定义的消息文件Person.proto放在同一个目录下,然后在命令行中进入该目录,执行下面的命令:
protoc.exe --java_out=./ Person.proto就在当前目录下生成了对应的java文件PersonProto.java下面可以在Java项目中使用上面编译好的PersonProto.java文件了,我们新建一个java项目,项目结构如下:
上面需要注意的是,我们在lib目录下引入了protobuf-java-2.5.0.jar包,这个包就是用来对ProtocolBuffer消息进行序列化和反序列化的.
下面定义一个Server类,用于处理客户端发送过来的消息,代码如下:
package com.demo.server; import com.demo.constant.Constants; import com.demo.msg.PersonBean; import com.google.protobuf.ByteString; import java.net.ServerSocket; import java.net.Socket; /** * Created by yubo7 on 2016/8/16. */ public class Server { public static void main(String[] args) throws Exception { ServerSocket ss = new ServerSocket(Constants.PORT); System.out.println("server started..."); Socket socket = ss.accept(); System.out.println("a client connected!"); //从输入流中解析出Person对象 PersonBean.Person person = PersonBean.Person.parseFrom(ByteString.readFrom(socket.getInputStream())); if(person != null) { System.out.println("server received data:\n" + person.toString()); } } } 下面定义一个Client类,用于生成一个Person类并发送给Server,代码如下: package com.demo.client; import com.demo.constant.Constants; import com.demo.msg.PersonBean; import java.io.OutputStream; import java.net.Socket; /** * Created by yubo7 on 2016/8/16. */ public class Client { public static void main(String[] args) throws Exception { Socket socket = new Socket("localhost", Constants.PORT); //构造一个Person对象 PersonBean.Person person = PersonBean.Person.newBuilder().setName("zhangsan") .setAge(20).setGender("male").build(); OutputStream os = socket.getOutputStream(); //将Person对象写到输出流中 os.write(person.toByteArray()); os.flush(); //这里注意一定要关闭流,否则服务端会报错 os.close(); System.out.println("client send person"); } } 上面的PORT为常量,定义在Constants类中,代码如下: package com.demo.constant; /** * Created by yubo7 on 2016/8/16. */ public class Constants { public static final int PORT = 9988; } 到这里就可以测试程序了,我们先启动Server,在控制台打印的内容如下图:然后再启动Client,在控制台打印的内容如下图:
然后再切换回Server的控制台,可以看到控制台中的打印如下图:
可以看到,控制台中打印了客户端发送过去的Person消息,这样,一个使用ProtocolBuffer来进行数据发送和接收的java程序就完成了。
本文源代码已托管到GitHub:https://github.com/yubo725/ProtocolBufferDemo
参考文章:http://www.ibm.com/developerworks/cn/linux/l-cn-gpb/
