Protocol Buffers 学习(1):定义一个消息

栏目: 服务器 · 发布时间: 6年前

内容简介:Protocol Buffers 学习(1):定义一个消息

首先让我们来看一个非常简单的例子。 假设你想定义一个消息格式,用来表示搜索请求,其中每个搜索请求都有三项:

  • 一个查询字符串
  • 你感兴趣的特定结果页
  • 以及每个页面的结果数

下边是用来定义消息类型的 .proto 文件

syntax = "proto3";

message SearchRequest {
  string query = 1;
  int32 page_number = 2;
  int32 result_per_page = 3;
}
  • 第一行表示使用的protocol版本是3,如果你不写这一条, protobuf 会认为你使用的是 protobuf2 ,而且,这行必须是第一行,前边也不能有注释
  • SearchRequest 这条消息定义了三个字段(名称/值对),每条消息都要包含这三个字段,每个字段都有一个名称和一个类型

字段类型说明

在上面的例子中,所有字段都是基本类型:两个整数(page_number和result_per_page)和一个字符串(query)。这些字段也可以是复合类型,包括枚举和其他消息类型

字段标签

消息定义中的每个字段都有唯一的编号标签,这些标记用于以消息二进制格式标识字段,消息开始使用之后就 不能修改

注意:

  • 值在1到15范围内的标签需要一个字节进行编码,包括标识号和字段类型
  • 在16到2047范围内的标签占用两个字节。

因此,你应该为非常频繁出现的消息元素保留标签1到15。记住要为可能在将来添加的频繁出现的元素留出一些空间。

最小的标签是1,最大的标签是 536870911 ,即 2^29 - 1 ,并且 19000 - 19999protobuf 系统保留标签,不能使用这几个

字段规则说明

一共有两种类型

  • singular: 一个符合规则的消息应该具备零个或者一个该字段
  • repeated: 一个符合规则的消息可以有零个或者任意个该字段,并且保留重复的顺序,在 proto3 中,基本类型的重复字段默认压缩编码

添加更多消息类型

可以在单个 .proto 文件中添加多个消息类型,例如

message SearchRequest {
  string query = 1;
  int32 page_number = 2;
  int32 result_per_page = 3;
}

message SearchResponse {
 ...
}

添加注释

可以使用 //.proto 文件添加注释。例如

message SearchRequest {
  string query = 1;
  int32 page_number = 2;  // Which page number do we want?
  int32 result_per_page = 3;  // Number of results to return per page.
}

保留字段(字段修改或者删除解决办法)

当消息类型更新或者删除时,这些被修改的字段的标签如果继续使用,会造成数据不正确的问题,这时需要把这些标签保留起来,防止跟旧版本的数据发生冲突。

(当使用JSON序列化时, 字段名称 也有可能存在这个问题),通俗来说,就相当于已经上线了使用A接口的一个APP,这个时候服务端如果想修改A接口的数据格式,只能新增一个接口,并且肯定不能使用A接口的地址

案例

message Foo {
  reserved 2, 15, 9 to 11;
  reserved "foo", "bar";
}

这就表示 2,15,9,10,11,"foo", "bar"都不能重复使用了

.proto 文件会生成什么?

当编译 .proto 文件时,编译器将根据你选择的语言生成对应代码,你需要使用文件中描述的消息类型,包括获取和设置字段值,将消息序列化 输出流,以及解析来自输入流的消息

  • 对于PHP,编译器会为每个消息生成一个类,用来描述该消息
  • 对于C ++,编译器从每个 .proto 生成 .h.cc 文件,并为您的文件中描述的每个消息类型指定一个类
  • 对于Java,编译器会为每个消息类型生成一个带有类的 .java 文件,以及用于创建消息类实例的特殊Builder类
  • Python有点不同, Python编译器生成一个模块,其中包含 .proto 中每个消息类型的静态描述符,然后使用元类在运行时创建必要的 Python 数据访问类
  • 对于Go,编译器会为文件中的每种消息类型生成一个具有类型的.pb.go文件
  • 对于Ruby,编译器生成一个包含消息类型的包含 Ruby 模块的.rb文件
  • 对于JavaNano,编译器输出与 Java 类似,但没有Builder类
  • 对于Objective-C,编译器从每个 .proto 生成一个 pbobjc.hpbobjc.m 文件,在文件中描述的每个消息类型都有一个类
  • 对于C#,编译器从每个 .proto 生成一个 .cs 文件,在文件中描述的每个消息类型都有一个类

以上所述就是小编给大家介绍的《Protocol Buffers 学习(1):定义一个消息》,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对 码农网 的支持!

查看所有标签

猜你喜欢:

本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们

Numerical Recipes 3rd Edition

Numerical Recipes 3rd Edition

William H. Press、Saul A. Teukolsky、William T. Vetterling、Brian P. Flannery / Cambridge University Press / 2007-9-6 / GBP 64.99

Do you want easy access to the latest methods in scientific computing? This greatly expanded third edition of Numerical Recipes has it, with wider coverage than ever before, many new, expanded and upd......一起来看看 《Numerical Recipes 3rd Edition》 这本书的介绍吧!

XML 在线格式化
XML 在线格式化

在线 XML 格式化压缩工具

HEX CMYK 转换工具
HEX CMYK 转换工具

HEX CMYK 互转工具