stream的实现其实和service一样是接口;
1. 普通服务,5小节就是此部分的实现
.proto文件:
rpc 方法名(变量类型)returns(变量类型){}
服务器:
func(grpc服务端结构体)方法名(ctx,入参类型指针)回参类型指针,error{
}
客户端:
返回值,错误 = 创建好的grpc客户端连接.方法名(ctx,入参)
2. 流式传入,返回是普通的(客户端流传入,服务端普通返回)
.proto文件:
rpc 方法名(stream 变量类型)returns(变量类型){}
服务器:
func(grpc服务端结构体)方法名(ctx,给定流式参数server)error{
server.Recv()//对流式数据进行接收,并判断是否EOF,然后可以再最后关闭之前,用sendAndClose传输数据回去;
}
客户端:
clientIn,错误 := 创建好的grpc客户端连接.方法名(ctx)
//数据必须是一端写一端读
err := clientIn.Send(&入参类型{
数据
})
3. 流式返回,输入参数是普通的(客户端普通传入,服务端流返回)
.proto文件:
rpc 方法名(变量类型)returns(stream 变量类型){}
服务器:
func(grpc服务端结构体)方法名(ctx,入参serve)error{
serve.Send()//返回流式数据
}
客户端:
clientIn,错误 := 创建好的grpc客户端连接.方法名(ctx)
//数据必须是一端写一端读
repos,err := clientIn.Recv()//不断读取,等待一个EOF,CloseSend()可以强制断开开源,但是不安全;
4. 流式出入(双向流):流式传入,流式返回,输入参数与返回都是流式(客户端和服务端都是流式)
.proto文件:
rpc 方法名(stream 变量类型)returns(stream 变量类型){}
服务器:
func(grpc服务端结构体)方法名(ctx,给定流式参数server)error{
var flagchan = make(chan bool)
//入
i := 0
go func(){
for{
i++
req,err := server.Recv()//对流式数据进行接收,并判断是否EOF,然后可以再最后关闭之前,用sendAndClose传输数据回去;
if i>10||err!=nil{
break
}else{
fmt.Println(req)
flag <- true//这也可以写入req的数据,但不重要
}
}
}
go func(){
for{
<- flag
serve.Send(&反参类型{})//返回流式数据
}
}
return nil
}
客户端:
clientIn,错误 := 创建好的grpc客户端连接.方法名(ctx)
//数据必须是一端写一端读
err := clientIn.Send(&入参类型{
数据
})