一个简单的go使用grpc的案例

今日学习grpc通信,做一个简单的小demo来验证效果

一,默认已经装好了环境

如果没有装环境,简单的装一下

1,装protocol Buffer

https://juejin.cn/post/7137709231624421412

2,装go的grpc包,其实就是go get 引入

go get github.com/golang/protobuf/protoc-gen-go

二,写一个A服务作为被调用方,B服务去调用A服务

新建一个A项目
在这里插入图片描述
建立一个目录用于存proto文件,并新建一个proto文件,这个随便命名
在这里插入图片描述
AService.proto

// 指定当前proto版本
// proto的语法注意分号,写go写习惯的话,会经常遗漏分号
syntax = "proto3";
// 指定生成proto生成的go文件的目录和包名,本身是一个路径,如果没有配置包名,最后的一个目录会被当做包名
option go_package = "../service";

// 定义request model,假设A服务有个User的一些操作的model
// 假设当前功能是传入userName 和 userPassword
message UserRequest{
  string user_name = 1; // 这里“=”后面的数字代表顺序,与真实值无关
  string user_password = 2;
}
// 定义response model
// 假设当前功能是返回userID和Token
message UserResponse{
  string user_id = 1;
  string user_token= 2;
}
// 定义服务能提供的服务
service UserService{
  // 定义具体的方法,此定义更像一个接口(interface),他不做具体实现,只是声明该Grpc能调用的方法
  rpc GetUserToken(UserRequest) returns(UserResponse);
}

进入到protobufFile目录下(cd protobufFile),执行生成
protoc --go_out=plugins=grpc:./ .\AServer.proto

这时候可以看到已经生成了service目录和一个pb.go文件
在这里插入图片描述
这个文件里可以看到刚才我们定义的service UserService,连proto文件里的注释也一并被拿了进来

在这里插入图片描述

所以下一部就是按照这个“接口”进行方法实现,当然,真正的业务拆分环境当中,都是先实现了方法,然后按服务拆分的时候做响应的接口编写,通常,我们称之为“暴露”,就是给其他服务暴露出来某某方法以供调用。

2,方法编写

在根目录下新建目录model,并新建user.go

package model

import (
   "context"
   "errors"
   "go-grpc-test-A/service"
)

var UserServiceServer = &userServiceServer{}

type userServiceServer struct {
}

func (u userServiceServer) GetUserToken(ctx context.Context, request *service.UserRequest) (*service.UserResponse, error) {
   // 模拟过程
   if request.UserName != "" && request.UserPassword != "" {
      response := service.UserResponse{
         UserId: "123",
         // 验证请求是否成功瞎写的,请不要在意
         UserToken: "你传入的名字和密码是:" + request.UserName + "," + request.UserPassword,
      }
      return &response, nil
   } else {
      err := errors.New("参数不对")
      return &service.UserResponse{}, err
   }
}
3,编写main方法
package main

import (
   "go-grpc-test-A/model"
   "go-grpc-test-A/service"
   "google.golang.org/grpc"
   "log"
   "net"
)

func main() {
   grpcServer := grpc.NewServer()
   // 这里第二个参数写我们已经实现接口的model包下的UserServiceServer
   service.RegisterUserServiceServer(grpcServer, model.UserServiceServer)
   listener, err := net.Listen("tcp", ":8001")
   if err != nil {
      log.Fatal("服务监听失败", err)
   }
   _ = grpcServer.Serve(listener)
}
4,编写调用方服务,命名为B

新建项目后,把A项目的service目录和pb.go文件一起copy过来,保持两个项目一致(真实工程当中当然不是手动保持一致),记得运行一下 go mod tidy 把依赖都拉上

在这里插入图片描述

编写B服务的main方法

package main

import (
   "context"
   "fmt"
   "go-grpc-test-B/service"
   "google.golang.org/grpc"
   "google.golang.org/grpc/credentials/insecure"
   "log"
)

func main() {
   // 建立一个链接,请求A服务
   // 真实项目里肯定是通过配置中心拿服务名称,发给注册中心请求真实的A服务地址,这里都是模拟
   // 第二个参数是配置了一个证书,因为没有证书会报错,但是我们目前没有配置证书,所以需要insecure.NewCredentials()返回一个禁用传输安全的凭据
   connect, err := grpc.Dial(":8001", grpc.WithTransportCredentials(insecure.NewCredentials()))
   if err != nil {
      log.Fatal(err)
   }
   // 记得关闭链接
   defer connect.Close()
   // 调用ASerer.pb.go里面的NewUserServiceClient
   client := service.NewUserServiceClient(connect)
   // 直接调用 A服务中的GetUserToken方法,注意,这是B服务,本地并没有该方法的实现
   response, err := client.GetUserToken(context.Background(), &service.UserRequest{UserName: "我是萝卜", UserPassword: "123456"})
   if err != nil {
      log.Fatal("调用gRPC方法错误: ", err)
   }

   fmt.Printf("调用gRPC方法成功,user_id = %s, user_token = %s", response.UserId, response.UserToken)
}
5,启动验证

先启动A服务,启动成功后,启动B服务来调用A服务


B服务已经能成功访问A服务下的GetToken方法,至此,Grpc调用成功
在这里插入图片描述

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值