近期比较火的开源项目go-zero是一个集成了各种工程实践的包含了Web和RPC协议的功能完善的微服务框架,今天我们就一起来分析一下其中的RPC部分zRPC。
zRPC底层依赖gRPC,内置了服务注册、负载均衡、拦截器等模块,其中还包括自适应降载,自适应熔断,限流等微服务治理方案,是一个简单易用的可直接用于生产的企业级RPC框架。
zRPC初探
zRPC支持直连和基于etcd服务发现两种方式,我们以基于etcd做服务发现为例演示zRPC的基本使用:
配置
创建hello.yaml配置文件,配置如下:
Name: hello.rpc // 服务名
ListenOn: 127.0.0.1:9090 // 服务监听地址
Etcd:
Hosts:
- 127.0.0.1:2379 // etcd服务地址
Key: hello.rpc // 服务注册key
创建proto文件
创建hello.proto文件,并生成对应的go代码
syntax = "proto3";
package pb;
service Greeter {
rpc SayHello (HelloRequest) returns (HelloReply) {}
}
message HelloRequest {
string name = 1;
}
message HelloReply {
string message = 1;
}
生成go代码
protoc --go_out=plugins=grpc:. hello.proto
Server端
package main
import (
"context"
"flag"
"log"
"example/zrpc/pb"
"github.com/tal-tech/go-zero/core/conf"
"github.com/tal-tech/go-zero/zrpc"
"google.golang.org/grpc"
)
type Config struct {
zrpc.RpcServerConf
}
var cfgFile = flag.String("f", "./hello.yaml", "cfg file")
func main() {
flag.Parse()
var cfg Config
conf.MustLoad(*cfgFile, &cfg)
srv, err := zrpc.NewServer(cfg.RpcServerConf, func(s *grpc.Server) {
pb.RegisterGreeterServer(s, &Hello{})
})
if err != nil {
log.Fatal(err)
}
srv.Start()
}
type Hello struct{}
func (h *Hello) SayHello(ctx context.Context, in *pb.HelloRequest) (*pb.HelloReply, error) {
return &pb.HelloReply{Message: "hello " + in.Name}, nil
}
Client端
package main
import (
"context"
"log"
"example/zrpc/pb"
"github.com/tal-tech/go-zero/core/discov"
"github.com/tal-tech/go-zero/zrpc"
)
func main() {
client := zrpc.MustNewClient(zrpc.RpcClientConf{
Etcd: discov.EtcdConf{
Hosts: []string{"127.0.0.1:2379"},
Key: "hello.rpc",
},
})
conn := client.Conn()
hello := pb.NewGreeterClient(conn)
reply, err := hello.SayHello(context.Background(), &pb.HelloRequest{Name: "go-zero"})
if err != nil {
log.Fatal(err)
}
log.Println(reply.Message)
}
启动服务,查看服务是否注册:
ETCDCTL_API=3 etcdctl get hello.rpc --prefix
显示服务已经注册:
hello.rpc/7587849401504590084
127.0.0.1:9090
运行客户端即可看到输出:
hello go-zero
这个例子演示了zRPC的基本使用,可以看到通过zRPC构建RPC服务非常简单,只需要很少的几行代码,接下来我们继续进行探索
zRPC原理分析
下图展示zRPC的架构图和主要组成部分
zRPC主要有以下几个模块组成:
- discov: 服务发现模块,基于etcd实现服务发现功能