Go Engineering - Foundation - API - RPC
RPC
- Client 通过本地调用,调用 Client Stub
- Client Stub 将参数打包(Marshalling)成一个消息,然后发送这个消息
- Client 所在的 OS 将消息发送给 Server
- Server 接收到消息后,将消息传递给 Server Stub(或者 Server Skeleton)
- Server Stub 将消息解包(Unmarshalling)后得到消息
- Server Stub 调用服务端的子程序,处理完成后,将最终结果按照相反的步骤返回给 Client
gRPC
概述
- gRPC:google Remote Procedure Call
- gRPC 是由 Google 开发的高性能、开源、跨语言的通用 RPC 框架,基于 HTTP 2.0,默认使用 Protocol Buffers 序列化
- gRPC 的特点
- 支持多语言
- 基于 IDL(Interface Definition Language)文件定义服务
- 通过 proto3 生成指定语言的数据结构、服务端接口和客户端 Stub
- 通信协议基于标准的 HTTP/2,支持特性:双向流、消息头压缩、单 TCP 的多路复用、服务端推送等
- 支持的序列化方式:Protobuf、JSON
- Protobuf 是语言无关的高性能序列化框架,可以减少网络传输流量、提高通信效率
Protocol Buffers
- Protocol Buffers 是由 Google 开发的序列化方法,可用作数据通信协议和数据存储格式,非常灵活高效
- Protocol Buffers 的传输性能非常优秀,常用于对数据传输性能要求比较高的系统中,作为数据传输格式
- Protocol Buffers 的特点
- 更快的传输速度:二进制序列化,与 JSON 和 XML 等文本序列化方式相比,可以节省大量 IO
- 跨平台多语言:protoc 基于 protobuf 定义文件,编译出不同语言的客户端或者服务端
- 非常好的扩展性和兼容性:可以更新已有的数据结构,而不会破坏和影响原有的程序
- 基于 IDL 文件定义服务:通过 proto3 生成指定语言的数据结构、服务端和客户端接口
- Protocol Buffers 在 gRPC 框架中发挥的作用
- 定义数据结构
- 定义服务接口
- 通过 protobuf 进行序列化和反序列化,提升传输效率
示例
定义服务
gRPC 支持定义 4 种类型的服务方法
- Simple RPC
- 客户端发起一次请求,服务端响应一个数据
rpc SayHello (HelloRequest) returns (HelloReply) {}
- Server-side streaming RPC
- 客户端发送一个请求,服务端返回数据流响应,客户端从流中读取数据直到为空
rpc SayHello (HelloRequest) returns (stream HelloReply) {}
- Client-side streaming RPC
- 客户端将消息以流的方式发送给服务器,服务器全部处理完成后返回一次响应
rpc SayHello (stream HelloRequest) returns (HelloReply) {}
- Bidirectional streaming RPC
- 客户端和服务端都可以向对方发送数据流,双方的数据可以同时互相发送
rpc SayHello (stream HelloRequest) returns (stream HelloReply) {}
1 | syntax = "proto3"; |
生成代码
1 | ❯ ls |
1 | type HelloRequest struct { |
实现 Server
1 | package main |
1 | ❯ go run server.go |
实现 Client
屏蔽了底层的网络通信细节(调用方便) + 入参和出参都是 Go 结构体(不需要打包和解包)
1 | package main |
1 | ❯ go run client.go |
optional + nil
1 | syntax = "proto3"; |
experimental_allow_proto3_optional:将 optional 字段编译成指针类型
1 | ❯ protoc --experimental_allow_proto3_optional --go_out=plugins=grpc:$GOPATH/src user.proto |
1 | type GetUserRequest struct { |
1 | package user |
RESTful vs gRPC
RESTful API 和 gRPC API 是合作关系,对内业务使用 gRPC API,对外业务使用 RESTful API