go grpc客户端与服务端连接简单使用
1.文件目录如下:
2.建立接口文件
在此之前需要对grpc的使用环境进行配置,网上例程很多,不再赘述
syntax = "proto3";
// 定义包名
option go_package = "/;test";
//package test;
// 可以定义多个服务,每个服务内可以定义多个接口
service Waiter {
// 定义接口 (结构体可以复用)
// 方法 (请求消息结构体) returns (返回消息结构体) {}
rpc Chat (Require) returns (Response) {}
//操作模式
rpc SetOptMode (Mode) returns (ResultCode) {}
}
// 定义 Req 消息结构
message Require {
// 类型 字段 = 标识号
string question = 1;
}
// 定义 Res 消息结构cd
message Response {
string answer = 1;
}
message Mode{
bool manual=1;
bool auto=2;
}
message Empty{}
message ResultCode {
int32 code = 1;
}
//.proto文件编译目录如下:
//D:\GOproject\grpc-test\src\test>protoc.exe --go_out=plugins=grpc:. test.proto
生成test.pb.go文件,命令如下
D:\GOproject\grpc-test\src\test>protoc.exe --go_out=plugins=grpc:. test.proto
2.创建服务端
package main
import (
"fmt"
"golang.org/x/net/context"
"google.golang.org/grpc"
"grpc-test/src/test"
"log"
"net"
)
var simpleSuccessCode = &test.ResultCode{
Code: 1,
}
// 业务实现方法的容器
type server struct{}
// 为server定义 DoMD5 方法 内部处理请求并返回结果
// 参数 (context.Context[固定], *test.Req[相应接口定义的请求参数])
// 返回 (*test.Res[相应接口定义的返回参数,必须用指针], error)
func (s *server) Chat(ctx context.Context, in *test.Require) (*test.Response, error) {
fmt.Println("chat方法询问:"+in.Question)
//return &test.Res{BackJson: "MD5 :" + fmt.Sprintf("%x", md5.Sum([]byte(in.JsonStr)))}, nil
return &test.Response{Answer: "i am ok "}, nil
}
func (s *server) SetOptMode(ctx context.Context, mode *test.Mode) (*test.ResultCode, error) {
fmt.Println("操作模式:",mode.Auto,mode.Manual)
return simpleSuccessCode , nil
}
func main() {
lis, err := net.Listen("tcp", ":8888") //监听所有网卡8028端口的TCP连接
if err != nil {
log.Fatalf("监听失败: %v", err)
}
s := grpc.NewServer() //创建gRPC服务
/**注册接口服务
* 以定义proto时的service为单位注册,服务中可以有多个方法
* (proto编译时会为每个service生成Register***Server方法)
* 包.注册服务方法(gRpc服务实例,包含接口方法的结构体[指针])
*/
test.RegisterWaiterServer(s, &server{})
/**如果有可以注册多个接口服务,结构体要实现对应的接口方法
* user.RegisterLoginServer(s, &server{})
* minMovie.RegisterFbiServer(s, &server{})
*/
// 在gRPC服务器上注册反射服务
//reflection.Register(s)
// 将监听交给gRPC服务处理
err = s.Serve(lis)
if err != nil {
log.Fatalf("failed to serve: %v", err)
}
}
3.创建客户端
package main
import (
"fmt"
"golang.org/x/net/context"
"google.golang.org/grpc"
"grpc-test/src/test"
"log"
)
type client struct {
receive test.WaiterClient
}
var c client=client{}
func main() {
// 建立连接到gRPC服务
conn, err := grpc.Dial("127.0.0.1:8888", grpc.WithInsecure())
if err != nil {
log.Fatalf("did not connect: %v", err)
}
// 函数结束时关闭连接
defer conn.Close()
// 创建Waiter服务的客户端
t := test.NewWaiterClient(conn)
c.receive= test.NewWaiterClient(conn)
fmt.Printf("格式%T=\n,c=%V", t,c)
// 模拟请求数据
res := "how are you"
// os.Args[1] 为用户执行输入的参数 如:go run ***.go 123
//if len(os.Args) > 1 {
// res = os.Args[1]
//}
c.OptMode()
// 调用gRPC接口
tr, err := t.Chat(context.Background(), &test.Require{Question: res})
if err != nil {
log.Fatalf("could not greet: %v", err)
}
log.Printf("服务端响应: %s", tr.Answer)
//value, err := t.SetOptMode(context.Background(), &test.Mode{Manual: false,Auto: true})
//fmt.Println("mode服务器响应%t\n",&value.Code)
}
func(c client)OptMode(){
value, err := c.receive.SetOptMode(context.Background(), &test.Mode{Manual: false,Auto: true})
if value==nil{
value= &test.ResultCode{}
fmt.Println("请求数据为nil")
}
fmt.Println("mode服务器响应%t\n",value,value.Code,err)
}
4.分别启动运动服务端和客户端
本人目前一直在用grpc,通信效率很高,使用起来也很方便,不断搬砖,加油