Go语言grpc和protobuf


Posted in Golang onApril 13, 2022

1. 什么是grpc和protobuf

1.1 grpc

gRPC是一个高性能、开源和通用的RPC框架,面向移动和HTTP/2设计。

目前提供C、Java和Go语言版本,分别是:

grpc,grpc-java,grpc-go.其中C版本支持C,

C++,Node.js,Python,Ruby,Objective-C,PHP和C#支持.

grpc遵循HTTP/2协议,是一个二进制协议

grpc与http一样,底层都是tcp连接,遵循socket套接字

RPC是指远程过程调用,两台服务器A,B。A(客户端)调用B(服务端)上的方法,由于不在同一个内存空间,不能直接调用,需要通过网络调用。

Go语言grpc和protobuf

1.2 protobuf

Protocol Buffer是一种协议。
Protocol Buffer 其实 是 Google出品的一种轻量 & 高效的结构化数据存储格式,性能比Json、XML真的强2-100倍!

protobuf经历了protobuf2和protobuf3,pb3比pb2简化了很多,目前主流的版本是pb3

protobuf优点:

1.性能好:
压缩性能;
序列化和发序列化快,比Json、XML强2-100倍;
传输速度快。

2.便捷性好:
使用简单,自动生成序列化和反序列化代码;
维护成本低,只维护proto文件
向后兼容,不必破坏旧格式
加密性好

3.跨语言,跨平台,支持各种语言

protobuf缺点:

1.通用性差,json可以任何语言都支持,但是protobuf需要专门的解析库

2.自解释性差,只有通过proto文件才能了解数据结构

2.go下grpc

2.1官网下载protobuf工具

官网:https://github.com/protocolbuffers/protobuf/releases

Go语言grpc和protobuf

2.2 下载go的依赖包

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

2.3 编写proto文件

option go_package = "./;proto";

解释:

./;:生成文件的路径

proto:生成文件的包名

hello.proto

syntax = "proto3";
package services;
option go_package = "./;proto";
service Greeter {
    rpc SayHello (HelloRequest) returns (HelloReply);
}
message HelloRequest {
    string name = 1;
}
message HelloReply {
    string message = 1;
}

2.4 生成hello.pb.proto文件

cd到proto目录下
命令:protoc -I . hello.proto   --go_out=plugins=grpc:.
命令解释:
protoc -I .:在当前路径下寻找hello.proto文件
--go_out=plugins=grpc:.  :生成go语言的proto文件放在当前路径下

Go语言grpc和protobuf

2.5 编写server端代码

Go语言grpc和protobuf

package main
import (
	"context"
	"file_test/grpc_go/proto"
	"net"

	"google.golang.org/grpc"
)
type Server struct {}
// 业务逻辑
func (s *Server) SayHello(ctx context.Context, request *proto.HelloRequest) (*proto.HelloReply, error) {
	res := &proto.HelloReply{
		Message: "hello " + request.Name,
	}
	return res, nil
}
// 启动rpc的server服务
func start() {
	// 1.实例化server
	g := grpc.NewServer()
	// 2.注册逻辑到server中
	proto.RegisterGreeterServer(g,&Server{})
	// 3.启动server
	lis,err:=net.Listen("tcp","127.0.0.1:8081")
	if err !=nil{
		panic("监听错误:"+err.Error())
	}

	err = g.Serve(lis)
	if err !=nil{
		panic("启动错误:"+err.Error())
	}
}
func main() {
	start()
}

2.6 编写client端代码

package main
import (
	"context"
	"file_test/grpc_go/proto"
	"fmt"

	"google.golang.org/grpc"
)
// rpc调用
func clientRpc(body map[string]string) (res *proto.HelloReply, err error) {
	name := body["name"]
	conn, err := grpc.Dial("127.0.0.1:8081", grpc.WithInsecure())
	if err != nil {
		return nil,err
	}
	defer conn.Close()
	rpc := proto.NewGreeterClient(conn)
	response, err := rpc.SayHello(context.Background(), &proto.HelloRequest{Name: name})
	if err != nil {
		return nil,err
	}
	return response,nil
}
// 业务代码
func start() {
	body := make(map[string]string)
	body["name"] = "jeff"
	response,err := clientRpc(body)
	if err!=nil{
		fmt.Println("rpc调用失败:",err)
		return
	}
	fmt.Println(response.Message)
}
func main() {
	start()
}
//结果:
hello jeff

2.7 python和go相互调用实践(跨语言调用)

proto文件共用。

1.开启python的server端,go的client端测试。

2.开启go的server端,python的clinet端测试。

以上就是golang下grpc框架的使用编写示例的详细内容!

Golang 相关文章推荐
Go Gin实现文件上传下载的示例代码
Apr 02 Golang
go语言中json数据的读取和写出操作
Apr 28 Golang
golang 如何用反射reflect操作结构体
Apr 28 Golang
解决golang结构体tag编译错误的问题
May 02 Golang
聊聊golang中多个defer的执行顺序
May 08 Golang
golang 实用库gotable的具体使用
Jul 01 Golang
Go 中的空白标识符下划线
Mar 25 Golang
victoriaMetrics库布隆过滤器初始化及使用详解
Apr 05 Golang
GO语言字符串处理函数之处理Strings包
Apr 14 Golang
Golang MatrixOne使用介绍和汇编语法
Apr 19 Golang
Go获取两个时区的时间差
Apr 20 Golang
Golang 并发编程 SingleFlight模式
Apr 26 Golang
Golang流模式之grpc的四种数据流
Apr 13 #Golang
Golang数据类型和相互转换
Apr 12 #Golang
Go语言的协程上下文的几个方法和用法
Apr 11 #Golang
Golang 1.18 多模块Multi-Module工作区模式的新特性
Apr 11 #Golang
golang三种设计模式之简单工厂、方法工厂和抽象工厂
Golang原生rpc(rpc服务端源码解读)
Apr 07 #Golang
Go并发4种方法简明讲解
You might like
PHP 字符串 小常识
2009/06/05 PHP
PHP 前加at符合@的作用解析
2015/07/31 PHP
PHP基于yii框架实现生成ICO图标
2015/11/13 PHP
php 截取GBK文档某个位置开始的n个字符方法
2017/03/08 PHP
JavaScript传递变量: 值传递?引用传递?
2011/02/22 Javascript
javascript 实现键盘上下左右功能的小例子
2013/09/15 Javascript
jQuery中appendTo()方法用法实例
2015/01/08 Javascript
javascript实现简单的省市区三级联动
2015/05/14 Javascript
浅析Node.js中的内存泄漏问题
2015/06/23 Javascript
javascript中SetInterval与setTimeout的定时器用法
2015/08/24 Javascript
js获取及修改网页背景色和字体色的方法
2015/12/29 Javascript
Bootstrap导航条可点击和鼠标悬停显示下拉菜单的实现代码
2016/06/23 Javascript
使用JavaScript判断手机浏览器是横屏还是竖屏问题
2016/08/02 Javascript
JS实现简单的浮动碰撞效果示例
2017/12/28 Javascript
从零开始搭建webpack+react开发环境的详细步骤
2018/05/18 Javascript
vue.js将时间戳转化为日期格式的实现代码
2018/06/05 Javascript
JS基于ES6新特性async await进行异步处理操作示例
2019/02/02 Javascript
详解微信小程序之一键复制到剪切板
2019/04/24 Javascript
微信小程序实现单个卡片左滑显示按钮并防止上下滑动干扰功能
2019/12/06 Javascript
JS实现斐波那契数列的五种方式(小结)
2020/09/09 Javascript
Vertx基于EventBus发送接受自定义对象
2020/11/16 Javascript
微信小程序绘制半圆(弧形)进度条
2020/11/18 Javascript
python3简单实现微信爬虫
2015/04/09 Python
Python使用Paramiko模块编写脚本进行远程服务器操作
2016/05/05 Python
python验证码识别教程之利用投影法、连通域法分割图片
2018/06/04 Python
python opencv将图片转为灰度图的方法示例
2019/07/31 Python
python hashlib加密实现代码
2019/10/17 Python
在django-xadmin中APScheduler的启动初始化实例
2019/11/15 Python
python deque模块简单使用代码实例
2020/03/12 Python
关于tf.matmul() 和tf.multiply() 的区别说明
2020/06/18 Python
纯CSS3实现鼠标滑过按钮动画第二节
2020/07/16 HTML / CSS
一套英文Java笔试题面试题
2016/04/21 面试题
授权委托书格式
2014/07/31 职场文书
小学国庆节活动方案策划书
2014/09/16 职场文书
python 中[0]*2与0*2的区别说明
2021/05/10 Python
收音机爱好者玩机13年,简评其使用过的19台收音机
2022/04/30 无线电