【gRPC】2 分鐘學會 Protocol Buffer 語法

語言: CN / TW / HK

highlight: vs2015

導讀

學習 gRPC 一定繞不過 proto 檔案(不清楚什麼是 proto 檔案的,請移步 【gRPC】5 分鐘入門掃盲)。筆者也是 gRPC 初學,寫這個短篇的目的非常純粹,就是幫助團隊新人用最短的時間掌握 proto 的基本用法,起碼能看懂。所以本文的內容不會面面俱到,一切以實用為主。

PS:本文最適合熟悉 ts 的同學。文末會附上文字版程式碼,方便大家 copy。

正文

Talk is cheap, show me the code. 沒有什麼比直接上程式碼對比更高效清晰的了。

Proto vs TS

image.png

小結

大概的規則如下: Proto | TS :-:|:-: message | interface service | class repeated | Array\<T> string | string int32/int64/float etc. | number

其他型別比較好理解,就不一一列舉了。還有兩點需要特別說明: - proto 中的欄位名會在 TS 裡被轉化成小駝峰(camelCase); - repeated 修飾的欄位名會被自動加 List 字尾。

看完以上內容,相信應付日常開發肯定沒問題了。高階應用就先不展開了,以目前筆者的程度估計還 cover 不住。

結語

也沒什麼好總結的了,來段最近看的《誡子書》中的一段作為結尾,然後祝大家身體健康,萬事如意吧。

夫君子之行,靜以修身,儉以養德。非淡泊無以明志,非寧靜無以致遠。夫學須靜也,才須學也,非學無以廣才,非志無以成學。淫慢則不能勵精,險躁則不能治性。年與時馳,意與日去,遂成枯落,多不接世,悲守窮廬,將復何及!——《誡子書》諸葛亮

文字程式碼

Proto

```ts syntax = "proto3";

package helloworld;

message HelloRequest { string name = 1; }

message RepeatHelloRequest { string name = 1; int32 count = 2; }

message HelloReply { string message = 1; }

message ListRequest { repeated int32 id = 1; string nil = 2; }

message ListReply { repeated string id = 1; string Data = 2; }

message TsMap { string feature = 1; string version = 2; string series = 3; }

message MapI { TsMap test_map1 = 1; TsMap test_map2 = 2; TsMap validate_map = 3; }

message MapRequest { MapI map = 1; repeated string do_safety_cars = 2; }

message MapReply { MapI map = 1; }

service Greeter { // unary call rpc SayHello(HelloRequest) returns (HelloReply);

rpc ListTest(ListRequest) returns (ListReply);

rpc MapTest(MapRequest) returns (MapReply); }

service Stream { // server streaming call rpc SayRepeatHello(RepeatHelloRequest) returns (stream HelloReply); } ```

TS

```ts import * as grpcWeb from "grpc-web";

interface HelloRequest { name: string; }

interface RepeatHelloRequest { name: string; count: number; }

interface HelloReply { message: string; }

interface ListRequest { idList: Array; nil: string; }

interface ListReply { idList: Array; data: string; }

interface TsMap { feature: string; version: string; series: string; }

interface MapI { testMap1?: TsMap; testMap2?: TsMap; validateMap?: TsMap; }

interface MapRequest { map?: MapI; doSafetyCarsList: Array; }

interface MapReply { map?: MapI; }

export class GreeterPromiseClient { constructor( hostname: string, credentials?: null | { [index: string]: string }, options?: null | { [index: string]: any } );

sayHello( request: HelloRequest, metadata?: grpcWeb.Metadata ): Promise;

listTest( request: ListRequest, metadata?: grpcWeb.Metadata ): Promise;

mapTest(request: MapRequest, metadata?: grpcWeb.Metadata): Promise; }

export class StreamPromiseClient { constructor( hostname: string, credentials?: null | { [index: string]: string }, options?: null | { [index: string]: any } );

sayRepeatHello( request: RepeatHelloRequest, metadata?: grpcWeb.Metadata ): grpcWeb.ClientReadableStream; } ```