Protobuf 的使用和demo (Java)

jopen 7年前

项目中有用到 protobuf 作跨平台的通信 , 自己也想写个demo学习实践一下, 于是有了本文。


*这个demo是基于java开发的


1.系统环境

Windows


2.所需软件和lib

1). protoc.exe 

2). protobuf-java-2.4.1.jar


3.demo简介

很简单的程序,基于java开发。功能是客户端把 "消息"(手机信息) 发送给 服务端。服务端收到消息后打印。


4.开发流程

1). 定义"消息"的结构,即书写接口定义文件(.proto文件)。本例中,消息包含了"手机信息"。

文件名 mobile.proto

文件内容如下:

message MobilePhone{    
            
    required string               brand = 1 ;    
    required Hardware          hardware = 2;
    repeated string              software = 3;                    

}

message Hardware {

    required int32                    rom = 1;
    required int32                    ram = 2;      
    required int32                    size = 3 ;    
    
}


2).通过定义的接口文件,生成Mobile.java

执行命令: protoc  --java_out=outputFile sourceFile

上述命令中outputFile 和 sourceFile 指 输出文件和源文件,需替换成实际文件(路径)名,如:

protoc  --java_out=./src   ./proto/mobile.proto



3).创建工程,编码

引入protobuf-java-2.4.1.jar

拷贝Mobile.java至工程

书写客户端,服务端代码。

具体代码如下:

客户端

package com.nevermore.client;    import java.net.Socket;    import com.nevermore.domain.Mobile;    public class Client {        /**       * @param args       */      public static void main(String[] args) throws Exception {          // TODO Auto-generated method stub          Socket socket = new Socket("127.0.0.1",3030);          Mobile.MobilePhone.Builder builder = Mobile.MobilePhone.newBuilder();          Mobile.Hardware.Builder hardware = Mobile.Hardware.newBuilder();          hardware.setRam(2).setRom(16).setSize(5);          builder.setHardware(hardware)                 .setBrand("Apple")                 .addSoftware("camera")                 .addSoftware("tecent")                 .addSoftware("browser")                 .addSoftware("player");          byte[] messageBody = builder.build().toByteArray();                int headerLen = 1;          byte[] message = new byte[headerLen+messageBody.length];          message[0] = (byte)messageBody.length;          System.arraycopy(messageBody, 0,  message, 1, messageBody.length);          System.out.println("msg len:"+message.length);          socket.getOutputStream().write(message);      }    }

服务端:

import java.net.ServerSocket;  import java.net.Socket;    import com.nevermore.domain.Mobile;  import com.nevermore.domain.Mobile.MobilePhone;    public class Server {        /**       * @param args       */      public static void main(String[] args) throws Exception {          // TODO Auto-generated method stub          ServerSocket serverSock = new ServerSocket(3030);          Socket sock = serverSock.accept();          byte[] msg = new byte[256];          sock.getInputStream().read(msg);          int msgBodyLen = msg[0];          System.out.println("msg body len:"+msgBodyLen);          byte[] msgbody = new byte[msgBodyLen];          System.arraycopy(msg, 1, msgbody, 0, msgBodyLen);          MobilePhone phone = Mobile.MobilePhone.parseFrom(msgbody);          System.out.println("Receive:");          System.out.println(phone.toString());      }    }


运行后服务端打印:

Receive:
brand: "Apple"
hardware {
  rom: 16
  ram: 2
  size: 5
}
software: "camera"
software: "tecent"
software: "browser"
software: "player"


至此完成,仅作笔记。