protobuf java any_protobuf3笔记

Protobuf3笔记

文件后缀

定义Proto的文件应以.proto为后缀。

语法版本

Proto文件的首行应指定语法版本:

syntax = "proto3"; // "proto2"

定义字段

在消息中,每个字段以下列方式定义:

type filed "=" tag ";"

如:

message SearchRequest {

string query = 1;

int32 page_number = 2;

int32 result_per_page = 3;

}

标签数字

出于性能考虑,在消息中,常用字段的标签最好小于15。这样可以降低消息序列化后的体积。

多消息

一个Proto文件中,可以定义多个消息。如:

message SearchRequest {

// ...

}

message SearchResponse {

// ...

}

注释

Proto使用C风格的注释。

编译输出

对于C++,protobuf为每个消息生成一个类,为每个proto文件生成一个.h头文件和一个.cc源代码文件。

对Java,protobuf为每个消息生成一个类和一个Builder类。

对于Go,protobuf为每个消息生成一个.pb.go源代码文件和一个结构体。

对Objective-C,protobuf为每个proto文件生成一个pbobjc.h头文件和一个pbobjc.m文件,为每个消息生成一个类。

常用标量类型

bool

string

bytes

int32

int64

uint32

uint64

double

float

默认值

类型

默认值

bool

false

bytes

[]

numeric

0

enum

FirstElement

Field

null

枚举类型

message SearchRequest {

string query = 1;

int32 page_number = 2;

int32 result_per_page = 3;

enum Corpus {

UNIVERSAL = 0;

WEB = 1;

IMAGES = 2;

LOCAL = 3;

NEWS = 4;

PRODUCTS = 5;

VIDEO = 6;

}

Corpus corpus = 4;

}

message EnumAllowingAlias {

option allow_alias = true;

UNKNOWN = 0;

STARTED = 1;

RUNNING = 1;

}

引用其他消息类型

message SearchResponse {

repeated Result results = 1;

}

message Result {

string url = 1;

string title = 2;

repeated string snippets = 3;

}

引用其他proto文件

import "myproject/other_protos.proto";

protoc参数

-I/–proto_path 指定proto文件目录。

内置类型

message SearchResponse {

message Result {

string url = 1;

string title = 2;

repeated string snippets = 3;

}

repeated Result results = 1;

}

message SomeOtherMessage {

SearchResponse.Result result = 1;

}

更新消息

字段标签

不得改动已存在的字段标签。新生成的代码可以解析旧消息。新增的字段会被设置为默认值。旧代码也可以解析新消息,新增的字段会被忽略。

删除字段

字段可以被删除。但已使用过的标签不得重复使用。

bytes和string

当字符串是UTF-8编码时,bytes和string可以兼容。

Any消息

Any消息是一个占位符,表示任意类型。使用Any消息时,需要引用google/protobuf/any.proto。

import "google/protobuf/any.proto";

message ErrorStatus {

string message = 1;

repeated google.protobuf.Any details = 2;

}

NetworkErrorDetails details = ...;

ErrorStatus status;

status.add_details()->PackFrom(details);

ErrorStatus status = ...;

for (const Any& detail : status.details()){

if (detail.Is()){

NetworkErrorDetails network_error;

detail.UnpackTo(&network_error);

...

}

}

OneOf消息

OneOf提供了一种类似C语言union结构体的机制,来降低存储体积。

message SampleMessage {

oneof test_oneof {

string name = 4;

SubMessage sub_message = 9;

}

}

SampleMessage message;

message.set_name("Joe");

assert(message.has_name());

Map消息

Map可以定义一组键值对。

map projects = 3;

声明包。

package foo.bar;

定义服务

service SearchService {

rpc Search (SearchRequest) returns (SearchResponse);

}

在Go中使用protobuf

示例proto

package tutorial;

option java_package = "com.example.tutorial";

option java_outer_classname = "AddressBookProtos";

message Person {

required string name = 1;

required int32 id = 2;

string email = 3;

enum PhoneType {

MOBILE = 0;

HOME = 1;

WORK = 2;

}

message PhoneNumber {

required string number = 1;

optional PhoneType type = 2 [default = HOME];

}

repeated PhoneNumber phone = 4;

}

生成的代码

调用方法

import (

"github.com/golang/protobuf/proto"

pb "path/to/generated/pb/file"

)

// ...

p := &pb.Person {

Id: 1234,

Name: "John Doe",

Email: "jdoe@example.com",

Phones: []*pb.Person_PhoneNumber {

{Number: "555-4321", Type: pb.Person_HOME},

},

}

out, err := proto.Marshal(p)

q := &pb.Person{}

err := proto.Unmarshal(in, q)

proto.MessageType(name string) reflect.Type

proto.Clone(pb Message) Message

Any消息在Go中的用法

Any消息可以表示任意类型的消息。在Go中使用Any消息的示例如下:

import "github.com/golang/protobuf/ptypes"

import "github.com/golang/protobuf/proto"

import "path/to/generated/pb"

// message Foo {

// google.protobuf.Any bar = 1;

// }

// message Bar {

// uint32 x = 1;

// }

bar := &pb.Bar{

X: 1,

}

body, err := ptypes.MarshalAny(bar)

if err != nil {

log.Fatal(err)

}

foo := &pb.Foo{

Bar: body,

}

注意事项

在使用proto.Unmarshal(buf, message)对消息进行反序列化时,缓冲区buf的长度应当等于消息的实际长度。否则会报告如下错误消息: proto: protocol.Message: illegal tag 0 (wire type 0)

在Java中使用protobuf

示例proto

package tutorial;

option java_package = "com.example.tutorial";

option java_outer_classname = "AddressBookProtos";

message Person {

required string name = 1;

required int32 id = 2;

string email = 3;

enum PhoneType {

MOBILE = 0;

HOME = 1;

WORK = 2;

}

message PhoneNumber {

required string number = 1;

optional PhoneType type = 2 [default = HOME];

}

repeated PhoneNumber phone = 4;

}

生成的代码

// Person

public boolean hasName();

public String getName();

public boolean hasId();

public int getId();

public boolean hasEmail();

public String getEmail();

public List getPhoneList();

public int getPhoneCount();

public PhoneNumber getPhone(int index);

// Person.Builder

public boolean hasName();

public java.lang.String getName();

public Builder setName(String value);

public Builder clearName();

public List getPhoneList();

public int getPhoneCount();

public PhoneNumber getPhone(int index);

public Builder setPhone(int index, PhoneNumber value);

public Builder addPhone(PhoneNumber value);

public Builder addAllPhone(iterable value);

public Builder clearPhone();

调用方法

Person john = Person.newBuilder()

.setId(1234)

.setName("John")

.addPhone(

Person.PhoneNumber.newBuilder()

.setNumber("555-4321")

.setType(Person.PhoneType.HOME))

.build();

john.writeTo(outputStream);

Person walliam = Person.parseForm(inputStream);

使用Gradle生成protobuf

google提供了生成protobuf的gradle插件,名称是com.google.protobuf。在使用时,需要在build.gradle中加入:

buildscript {

repositories {

mavenCentral()

}

dependencies {

classpath 'com.google.protobuf:protobuf-gradle-plugin:0.8.1'

}

}

apply plugin: 'java'

apply plugin: 'com.google.protobuf'

protobuf {

generatedFilesBaseDir = '$projectDir/src'

protoc {

// use local protoc

// path = '/usr/local/bin/protoc'

// or, get from repo

artifact = 'com.google.protobuf:protoc:3.3.0'

}

plugins {

grpc {

artifact = 'io.grpc:protoc-gen-grpc-java:1.4.0'

}

}

generateProtoTasks {

all()*.plugins {

grpc {}

}

}

}

repositories {

mavenCentral()

}

dependencies {

compile 'com.google.protobuf:protobuf-java:3.3.1'

compile 'io.grpc:grpc-netty:1.4.0'

compile 'io.grpc:grpc-protobuf:1.4.0'

compile 'io.grpc:grpc-stub:1.4.0'

/* for Android client, use

compile 'io.grpc:grpc-okhttp:1.4.0'

compile 'io.grpc:grpc-protobuf-lite:1.4.0'

compile 'io.grpc:grpc-stub:1.4.0'

*/

}

sourceSets {

main {

proto {

srcDir 'src/main/protobuf'

include '**/*.proto'

}

}

}

然后执行:

gradle build

如果只需要生成java源代码文件,可以执行:

gradle generateProto

参考资料

修订记录

2016年05月03日 建立文档。

2016年08月11日 修订。

2017年07月28日 改为rst格式。

2017年07月28日 增加gradle部分。

2017年08月04日 修订例子。

2017年08月07日 增加在Go中使用Any消息的例子。

2018年08月06日 修正错别字;修改日期格式。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/487509.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

108页报告一文看懂光刻机,看国产替代如何破局【附下载】

来源:方正证券光刻机是人类文明的智慧结晶,被誉为半导体工业皇冠上的明珠。光刻机作为前道工艺七大设备之首,价值含量极大,在制造设备投资额中单项占比高达23%,技术要求极高,涉及精密光学、精密运动、高精度…

【bzoj 3601】一个人的数论 (莫比乌斯反演+伯努利数)

题解: (吐槽:网上题解那个不严谨猜测真是没谁了……关键是还猜得辣么准……) 直接化简到求和那一段: $f_{d}(n)\sum_{t|n}\mu(t)t^{d}\sum_{i1}^{\frac{n}{t}}i^{d}$ $设S_{d}(T)\sum_{i1}^{T}i^{d}$ 那这个是什么呢&a…

院士论坛|李德仁:测绘遥感与智能驾驶

来源:测绘学报未来智能实验室的主要工作包括:建立AI智能系统智商评测体系,开展世界人工智能智商评测;开展互联网(城市)云脑研究计划,构建互联网(城市)云脑技术和企业图谱…

ansible编译httpd playbook示例

以下是playbook的内容。它的处理流程是: 1.先在本地下载apr,apr-util,httpd共3个.tar.gz文件。 2.解压这3个文件。 3.安装pcre和pcre-devel依赖包。 4.编译安装apr。 5.编译安装apr-util。 6.编译安装httpd。 ---- hosts: alltasks: - name: download apr,apr-util,…

java jquery post_jquery js post变量set和get for post

我需要从php页面发送一些参数到另一个动态发布电子邮件,如果我发送硬编码的值是好的,但如果我在文本字段上发送值,它不起作用,这里的代码请求发送邮件的页面$otroYa other.val();console.log (other.val()); //shows value ok of…

深度报告:一文看懂生物芯片产业

来源:赛迪顾问生物芯片技术起源于二十世纪八十年代,也被称为“微流控技术”、“芯片实验室”等。生物芯片技术能够在邮票大小的芯片上,进行较为复杂的生物、化学、物理等实验,为制作成本低、样本少、时间短、操作简单的医疗仪器提…

java 设计模式 优缺点_java设计模式2:原型模式(机制\优缺点分析\使用场景)...

1、 原型模式实现机制原型模式在设计模式中相对比较简单,它直接通过实现 Cloneable接口,再重写 clone()方法返回想要的对象就OK 了。一起来看下代码 :public class ProtoType implements Cloneable {public ProtoType(){System.out.println(&…

人机融合的难点

来源:人机与认知实验室【一个深度态势感知者的周围充满了各种各样的暗示和提醒。】“我小时候读过很多科幻小说。其中一个最常见的主题是“人与机器”,它经常以机器人的形式变得自我意识和威胁人类。这一主题也成为了《终结者》和《黑客帝国》等好莱坞电…

asp.net core权限模块的快速构建

大部分系统都会有权限模块,别人家系统的权限怎么生成的我不知道,我只知道这样做是可以并且挺好的。 文章中只对asp.net core的部分代码进行说明 呃 记录~,mvc版本自行前往仓库查阅 代码中的一些特性标记后面列出,或前往仓库查看~ 1.根据特性标…

深度长文:AMD的崛起、衰落与复兴

来源:内容编译自「techspot」,谢谢。AMD是最早的大型微处理器设计者之一,近50年来一直是技术爱好者之间争论的话题。它的历史构成了一个激动人心的故事——充满了英雄式的成功,愚蠢的错误。在其他半导体公司来来往往的时候&#x…

数据结构-使用两个栈实现一个队列

1:如何只使用stack实现queue呢?我们知道stack是先进后出的(FIFO),而queue是先进先出的(FIFO)。也就是说,stack进行了一次反向。如果进行两次反向,就能实现queue的功能&am…

5G时代下,边缘计算产品的未来展望

来源:北京物联网智能技术应用协会首发于人人都是产品经理。一、边缘计算市场潜力1. 5G基建如火如荼,万物互联互融将成为新战场2019年6月6号上午工信部宣布正式为中国移动、中国联通、中国电信、中国广电四家企业颁发5G牌照,中国正式进入5G元年…

使用Xcode进行iOS设备无线调试

设备环境:Mac OSX 10.12.5、iOS11、Xcode9PS:这是WWDC2017的新功能,iOS11以上,Xcode9这是刚性要求。这个功能不好找,就记下来了 手机连接上Xcode,打开Xcode菜单:Windows->Device and Simulators。找到连…

java 请求url 返回数据_java后台发起get请求获取响应数据|chu

本文实例为大家分享了java后台发起get请求获取响应数据,供大家参考,具体内容如下学习记录:话不多说直接上代码:package com.jl.chromeTest; import java.io.BufferedReader; import java.io.InputStreamReader; import java.net.H…

Android Studio 设置字体

File->Settings->Editor->Colors & Fonts->Font->Editor Font 转载于:https://www.cnblogs.com/WJQ2017/p/7608370.html

这三个博弈论新趋势,正深刻影响深度强化学习

来源 | AI科技评论作者 | Jesus Rodriguez编译 | 亚尔曼•佩皮校对 | 丛末 & Camel博弈论在现代人工智能(AI)解决方案中正扮演着至关重要的角色,深度强化学习(DRL)正是积极拥抱博弈论的头等公民。从单智能体程序到…

Beam概念学习系列之Pipeline 数据处理流水线

不多说,直接上干货! Pipeline 数据处理流水线 Pipeline将Source PCollection ParDo、Sink组织在一起形成了一个完整的数据处理的过程。 Beam概念学习系列之PCollection数据集 Beam概念学习系列之PTransform数据处理转载于:https://www.cnblogs.com/zlslc…

美国再出半导体新法案!1800亿谋求芯片制造振兴

文章来源:EE Times、James E.Risch芯东西(ID:aichip001)编 | 董温淑芯东西7月1日消息,上周,多位美国两党议员共同提出《2020美国晶圆代工法案(AFA,The American Foundries Act Of 20…

stackexchange.mysql_.net core使用redis基于StackExchange.Redis

.net core使用redis基于StackExchange.Redis教程,具体如下一.添加引用包StackExchange.RedisMicrosoft.Extensions.Configuration二.修改配置文件 appsettings.json{"RedisConfig": {"Redis_Default": {"Connection": "127.0.0.…

Apache网站服务

Apache 下载地址: http://mirror.bit.edu.cn/apache/httpd/相关软件下载地址:http://mirror.bjtu.edu.cn/apache/apr/apr          http://mirror.bjtu.edu.cn/apache/apr/apr-utilApache 简介: 进程技术,高资源消耗&…