对码当歌,猿生几何?

go protobuf应用实例分析

go protobuf应用实例分析 

1) 安装protoc, 直接下载的linux编译好的protoc编译器,然后go get 一个go get -u github.com/golang/protobuf/protoc-gen-go 插件,编grpc

译好放在go bin里面。

20190306153517370.png

2) 二进制文件分析 0x08为protoc编译标志他检测有此标志的文件才解析

0x63 也就是协议中的Id字段啦, 99 = 0x63

0x66 0x75  0x63 0x6b   就是协议中 是Str字段啦   fuck

这里我对比了potobuf2 protobuf3产生的二进制都是一样的,只是3的语法

变化了哈。

3) message指令定义一个结构体拉,和我们用c实现一个协议用结构体一样,这里

他俩等价的底层存储的都是结构体的二进制啦

syntax = "proto3";
package msg;
message HelloWorld

{

    int32     id = 1; // ID
    string   str = 2; // str
    //optional int32     opt = 3; //optional field
    int32     opt = 3; //proto3 默认字段可选
    message Person {
      string name = 1;
      int32 age = 2;
    }
    int64 i64 = 4;
}
package mainimport proto "github.com/golang/protobuf/proto"import (
  "fmt"
  "os""msg") func main() {
      msg := &msg.HelloWorld{/* Id: proto.Int32(10),
      Str: proto.String("hello") ,*/
      Id: int32(99),
      Str: string("fuck"),
  }

      path := string("./test3.txt")
      f, err := os.Create(path)
      if err != nil {
          fmt.Printf("failed: %s", err)
          return
      }

  defer f.Close()
  buffer, err := proto.Marshal(msg)
  f.Write(buffer)}in, err := ioutil.ReadFile(fname)if err != nil {
  log.Fatalln("Error reading file:", err)}msg := &msg.HelloWorld{}if err := proto.Unmarshal(in, msg); err != nil {
  log.Fatalln("Failed to parse msg:", err)}