gRPC超时机制

简介

    其实不止再微服务中,再平常的网络请求或者第三方系统进行交互都需要设置超时时间;
为什么需要超时机制?

    总体上讲,肯定是为了增加系统的可靠性:

  • 系统自我保护:快速失败,在业务最大允许等待时间内未收到返回数据,主动放弃等待,释放占用资源,避免请求不断累积带来的客户端雪崩效应
  • 成功率:服务处理超时的原因有很多,但常见的超时都是短暂的,主要是:网络抖动或者网络拥塞;这些短时间影响服务端状态的情况而造成请求成功率下降,需要补救措施;简单的补救有超时重试操作:当请求超时后,将会重试到非当前服务器,降低重试超时的几率

代码

proto

syntax = "proto3";
option go_package = ".;proto";

service Greeter{
  rpc SayHello(HelloRequest) returns (HelloReplay);
}

message HelloRequest{
  string name = 1;
}

message HelloReplay{
  string message = 1;
}

.pb.go

// 具体代码省略,使用名称生成即可
protoc -I . hello.proto --go_out=plugins=grpc:.

Server

package main

import (
	"ShopBefore/rpc/grpc_timeout/proto"
	"context"
	"google.golang.org/grpc"
	"net"
	"time"
)

type Server struct{}

func (s Server) SayHello(ctx context.Context, request *proto.HelloRequest) (*proto.HelloReplay, error) {
	// Server里面休眠5s
	time.Sleep(5 * time.Second)
	return &proto.HelloReplay{Message: "hello " + request.Name}, nil
}

func main() {
	server := grpc.NewServer()
	proto.RegisterGreeterServer(server, &Server{})
	listen, _ := net.Listen("tcp", ":8081")
	_ = server.Serve(listen)
}

Client

package main

import (
	"ShopBefore/rpc/grpc_timeout/proto"
	"context"
	"fmt"
	"google.golang.org/grpc"
	"google.golang.org/grpc/credentials/insecure"
	"google.golang.org/grpc/status"
	"time"
)

func main() {
	conn, _ := grpc.Dial("localhost:8081", grpc.WithTransportCredentials(insecure.NewCredentials()))
	client := proto.NewGreeterClient(conn)
	// 配置超时时间3s
	ctx, _ := context.WithTimeout(context.Background(), 3*time.Second)
	res, err := client.SayHello(ctx, &proto.HelloRequest{Name: "番茄炒蛋"})
	if err != nil {
		err, ok := status.FromError(err)
		if !ok {
			panic("解析error失败")
		}
		// DeadlineExceeded
		fmt.Println(err.Code())
		// context deadline exceeded
		fmt.Println(err.Message())
	} else {
		fmt.Println(res.Message)
	}
}

你可能感兴趣的:(grpc入门和进阶,golang,rpc,网络)