文末有源码下载链接!
1、什么是RPC?gRPC是什么?
RPC是Remote Procedure Call的缩写,中文是远程过程调用的意思。让程序像调用本地函数一样去调用远在另一台服务器上的函数。
gRPC是Google开源的高性能RPC框架。它的特点是:
使用HTTP/2
使用Protobuf(二进制序列化)
自动生成客户端与服务端代码
内置流式通信
高性能、跨语言
gRPC专为微服务架构打造。
2、gRPC的工作流程
第一步:用protobuf(.proto文件)定义接口与数据结构
第二步:用protoc工具自动生成客户端和服务的代码
第三步:实现服务端接口
第四步:写客户端
第五步:使用HTTP/2+二进制传输进行通信
[.proto 文件] → protoc → [Server + Client ] →
Server 实现 ←→ Client 像调用本地函数一样调用
3、gRPC示例
我们以商品管理为例
3.1 定义proto文件 proto/goods.proto
syntax = "proto3";
package goods;
option go_package = "./proto/goods";
service GoodsService {
rpc GetGoods (GetGoodsRequest) returns (GetGoodsResponse) {}
}
message GetGoodsRequest {
int64 id = 1;
}
message GetGoodsResponse {
int64 id = 1;
string name = 2;
float price = 3;
int64 stock = 4;
}
3.2 生成代码
$ protoc --go_out=. --go-grpc_out=. goods.proto
这里生成的代码比较长,只做展示用,源码在文末下载,注意:生成的代码不要去改动
3.3 实现服务端
//proto_impl/goods.impl.go
package protoimpl
import (
"context"
"golang_per_day_29/proto/goods"
)
type GoodsServiceServer struct {
goods.UnimplementedGoodsServiceServer
}
func (s *GoodsServiceServer) GetGoods(ctx context.Context,
req *goods.GetGoodsRequest) (*goods.GetGoodsResponse, error) {
return &goods.GetGoodsResponse{
Id: req.Id,
Name: "Codee君",
Price: 99.99,
Stock: 1000,
}, nil
}
//main.go
package main
import (
"golang_per_day_29/proto/goods"
protoimpl "golang_per_day_29/proto_impl"
"net"
"google.golang.org/grpc"
)
func main() {
lis, _ := net.Listen("tcp", ":50051")
s := grpc.NewServer()
goods.RegisterGoodsServiceServer(s,
&protoimpl.GoodsServiceServer{})
s.Serve(lis)
}
//启动服务
go run .
3.4 客户端调用
// main_test.go
func TestGrpc(t *testing.T) {
conn, _ := grpc.Dial("localhost:50051", grpc.WithInsecure())
defer conn.Close()
client := goods.NewGoodsServiceClient(conn)
res, _ := client.GetGoods(context.Background(),
&goods.GetGoodsRequest{Id: 1})
if res.GetId() != 1 {
t.Error("grpc client error")
}
}
3.5 测试一下
4、gRPC为什么适合微服务?
gRPC有明显的优势:快、稳定、省数据、省CPU、规范。
5、gRPC和REST对比
| 对比点 | REST(HTTP+JSON) | gRPC(HTTP/2+Protobuf) |
| 性能 | 慢 | 快上加快 |
| 传输格式 | JSON | 二进制protobuf |
| 连接类型 | 短连接/无状态 | 长连接,多路复用 |
| 代码生成 | 自己用手敲 | 自动生成 |
| 流式通讯 | 不擅长 | 强项 |
| 浏览器支持 | 好 | 原生支持差 |
结论:外部API面向前端-> REST, 内部服务之间通信->gRPC
*源码地址*
1、公众号“Codee君”回复“每日一Go”获取源码
2、源码获取链接: pan.baidu.com/s/1B6pgLWfS… 提取码: jc1s
如果您喜欢这篇文章,请点赞、推荐+分享给更多朋友,万分感谢!