每周五11:45 按时送达
当然了,也会时不时加个餐~
我的第「224」篇原创敬上
做技术的都知道,程序之间的通讯,常用的方式有两种,RPC 和 HTTP。普遍的共识是系统内部的各个子系统之间的通讯用 RPC,与外部系统之间的通讯用 HTTP。
为了避免需要分别编写两套契约文件来生成两套 API(.proto 和 .api),如果能够根据同一份契约文件生成两套 API 的代码就太棒了。
Z哥目前所在的公司,rpc 使用的框架是 gRPC,所以自然先想得是,是否能够根据一份 proto 文件,同时生成 gRPC 和 HTTP 的 stub 代码呢。
网上很快就找到了一个符合要求的框架。相信不少 gopher 们应该也听说过或者正在使用。
https://github.com/grpc-ecosystem/grpc-gateway
通过一份 proto 文件,在生成 gRPC 代码的同时生成一个基于 HTTP1.1 + JSON 的反向代理 gateway,如此一来,既可以通过 gRPC 的方式直接调用实际的 server ,也可以通过反向代理中转一次来访问 server。
具体的使用方式看 github 上的官方教程即可,Z 哥和你主要聊一下其中可能会遇到的卡点。毕竟国内的网络情况你懂的,有些操作可能会遇到一些困难。
教程里提供了两种来操作,一种是通过基础工具 protoc 来操作,另一种是通过一个基于 protoc 封装的工具 buf 来操作。protoc 可以基于 go mod 来安装,鉴于 go mod 还有国内的镜像站点可以解决访问的困难,建议不会科学上网的小伙伴通过 protoc 来操作,因为你没办法成功安装 buf。
/02 手动下载 googleapis 的repo/
然后,当你定义 gateway 的时候,需要引入一些 google 的 packages,怎么办呢?直接去 github 上下载,具体地址是:
https://github.com/googleapis/googleapis
如果可以的话,建议把整个仓库都下载下来,否则就单独下载教程里提到的4个文件即可。
特别要注意的是,在 googleapis/google/目录下缺少的 protobuf 相关文件需要到下面的 repo 里去下载,并且放到 googleapis/google/目录下。
https://github.com/protocolbuffers/protobuf/tree/main/src/google/protobuf
官方教程里的 protoc -I . 只会查找当前命令执行所在目录的范围,所以如果你下载的 googlesapi 不存放在当前目录下,则需要增加额外信息指定一下查找目录。
指定的方式是再增加一个 -I,命令如下(其中第二行就是新增的用于查找 google packages 的目录):
protoc -I ./ \
-I $GOPATH/src/googleapis\
--grpc-gateway_out ./gen/go \
--grpc-gateway_opt logtostderr=true \
--grpc-gateway_opt paths=source_relative \
--grpc-gateway_opt generate_unbound_methods=true \
your/service/v1/your_service.proto
如果还有其它目录需要查找,那么继续增加 -I 即可。
好了需要注意的点就是以上3个,官方教程中提到的三个命令可以一起执行,这样便可同时生成 gRPC server、gateway 和 swagger.json :
protoc -I ./ \
-I $GOPATH/src/googleapis\
--go_out ./gen/go/ --go_opt paths=source_relative \
--go-grpc_out ./gen/go/ --go-grpc_opt paths=source_relative \
--grpc-gateway_out ./gen/go/ \
--grpc-gateway_opt logtostderr=true \
--grpc-gateway_opt paths=source_relative \
--grpc-gateway_opt generate_unbound_methods=true \
--openapiv2_out . --openapiv2_opt logtostderr=true \
your/service/v1/your_service.proto
关于一些gRPC-Gateway的其它用法可以参考:
https://grpc-ecosystem.github.io/grpc-gateway/
好了,这篇呢,Z哥和你分享了如何用一份 proto 文件同时生成 gRPC 和 HTTP 的 Stub 代码以及 Swagger 文档。
如此不但可以提高效率,还可以避免维护两份不同的契约文件所带来不一致风险,希望对你有所帮助。
推荐阅读:
原创不易,如果你觉得这篇文章还不错,就「点赞」或者「在看」一下吧,鼓励我的创作 :)
跨界架构师
坚持原创。专注大型互联网技术,涉猎产品、运营。
189篇原创内容
Official Account
如果你有关于软件架构、分布式系统、产品、运营的困惑
可以试试点击「阅读原文」