在js中使用grpc(包括代理)后端使用Go
创始人
2024-03-13 05:45:06
0

叙述

最近在研究web端的聊天系统,准备使用grpc作为通讯协议,因为客户端要主动的接受到消息,所以想要使用双向流的grpc。
但是经过几天的研究发现,grpc在浏览器上是不支持的,因为浏览器使用的协议是http1.1,而grpc底层使用的是http2协议,所以不兼容。
但是由于前端会有使用到grpc的需求,所以grpc官方也给出了一套解决方案,grpc-web
实际上grpc-web在浏览器中使用的还是http协议,但是会使用到代理,将http请求转换成grpc请求,‘欺骗’ 服务器,关于代理方面,我下文中会解释
而且grpc-web还有一个重要的缺点不支持双向流和客户端流,这显然与我最初的本意违背,但是毕竟研究了那么久,还是写篇博客纪念一下

前端

我是将前端作为客户端使用的,所以这边这只会写客户端的代码,想要服务端的要使用node才行,纯浏览器就不要考虑服务端了

下载

1.下载protoc
下载 v3.20.1版本,不要下载最新版本 因为最新版本有缺陷,跟grpc-web搭配不了
我下载的是protoc-3.20.1-win64.zip包

下载地址: https://github.com/protocolbuffers/protobuf/releases

解压这个文件之后,将bin目录下的 protoc.exe文件复制到 Go目录下的bin文件夹下面,如果不知道Go目录在哪里的话,可以打开环境变量的path,可以看到

2.下载protoc-gen-grpc-web

下载地址 :https://github.com/grpc/grpc-web/releases/download/1.4.2/protoc-gen-grpc-web-1.4.2-windows-x86_64.exe

下载完成之后,将这个应用程序同样放到Go的bin目录下,并将其名字改成protoc-gen-grpc-web.exe

这两部都好了之后,go的bin目录下长这个样子:
在这里插入图片描述

编辑

然后就可以开始写代码啦
将官网的grpc-web的代码拉下来,其实只
拉取完成后,使用cscode或其他软件打开
你存放项目的目录\grpc-web\net\grpc\gateway\examples\helloworld 这个文件夹
没错,下载这么大的项目,只需要用这么一小个目录

在终端输入

npm install  

将他的所需要依赖下载下来

在项目(helloworld)根目录下创建文件夹hello,用于存放等下由命令生成的pb 和grpc_pb文件

在终端运行命令(如果你移动了proto文件的位置,那么要切换到在proto所在文件夹下运行命令)

protoc  helloworld.proto --js_out=import_style=commonjs:../hello --grpc-web_out=import_style=commonjs,mode=grpcwebtext:../hello

然后就可以看到
在这里插入图片描述

编辑client.js文件

改变后的client.js文件

const { HelloRequest, RepeatHelloRequest, HelloReply } = require('./hello/helloworld_pb.js');
const { GreeterClient } = require('./hello/helloworld_grpc_web_pb.js');var client = new GreeterClient('http://localhost:9090', null, null);var but = document.getElementById('bu')//这里设置了一个点击事件,当点击按钮的时候,再向服务端发送请求
//按钮要联系到index.html文件上
but.onclick  = function () {var request = new HelloRequest();request.setName('World');client.sayHello(request, {}, (err, response) => {if (err) {console.log(`Unexpected error for sayHello: code = ${err.code}` +`, message = "${err.message}"`);} else {console.log(response.getMessage());}});
}// server streaming call
// var streamRequest = new RepeatHelloRequest();
// streamRequest.setName('World');
// streamRequest.setCount(5);// var stream = client.sayRepeatHello(streamRequest, {});
// stream.on('data', (response) => {
//   console.log(response.getMessage());
// });
// stream.on('error', (err) => {
//   console.log(`Unexpected stream error: code = ${err.code}` +
//               `, message = "${err.message}"`);
// });

将clien.js文件打包成main.js

执行命令

npx webpack client.js

如果中途有需要确认的命令 直接yes或者y就好

然后就会生成一下文件
在这里插入图片描述

将main.js引入index.html,并编辑index.html


gRPC-Web Example

Open up the developer console and see the logs for the output.

Go后端

设置proto文件

将前端的helloworld.proto文件复制到后端go项目中,创建hello目录

syntax = "proto3";package helloworld;
option go_package = "../hello";//这里相较于前端增加一行,这里是pb和grpc_pb文件生成的目录service Greeter {// unary callrpc SayHello(HelloRequest) returns (HelloReply);// server streaming callrpc SayRepeatHello(RepeatHelloRequest) returns (stream HelloReply);
}message HelloRequest {string name = 1;
}message RepeatHelloRequest {string name = 1;int32 count = 2;
}message HelloReply {string message = 1;
}

在这里插入图片描述

生成pb和grpc_pb文件

在终端中进入proto文件所在的目录

cd pbfiles

然后运行 命令

protoc -I . --go_out=. helloworld.proto --go-grpc_out=. helloworld.proto

生成一下两个文件
在这里插入图片描述

创建服务端

helloWorldServer.go

package mainimport ("context""fmt""google.golang.org/grpc"protos "grpc_server/hello""net"
)type helloServer struct {protos.UnimplementedGreeterServer
}func (s *helloServer) SayHello(ctx context.Context, req *protos.HelloRequest) (*protos.HelloReply, error) {//获取到的客户端传来的值fmt.Println("服务端被调用了")name := req.GetName()fmt.Printf("Data from client : %s\n", name)//将值传回到客户端return &protos.HelloReply{Message: "我是服务端",}, nil
}func main() {//创建rpc 服务器server := grpc.NewServer()protos.RegisterGreeterServer(server, &helloServer{})//创建 Listen,监听 TCP 端口listen, err := net.Listen("tcp", ":8080")if err != nil {panic(err)}defer listen.Close()//开启服务err = server.Serve(listen)if err != nil {panic(err)}
}

配置代理

代理我这边使用的是grpcwebproxy,官方的那个用的envoy.yaml,是用在后端的,不会用,换了个简单的

下载

https://github.com/improbable-eng/grpc-web/releases/tag/v0.13.0

在这里插入图片描述
然后将这个exe文件放到helloworld项目的根目录里面
在这里插入图片描述

运行exe文件

在exe文件所在目录下执行命令

grpcwebproxy-v0.15.0-win64.exe --allow_all_origins --backend_addr=localhost:8080 --run_tls_server=false --server_http_debug_port=9090 --allow_all_origins=true

如果你和我的grpcwebproxy版本不同,记得换成你的grpcwebproxy的名字,不然报错

至于这个命令的详解,可以去看这篇博客grpcwebproxy代理服务2步启动

运行

先开启服务端
在这里插入图片描述

后开启客户端

在index.html文件中 按F5或Fn+F5,就可以开启,并点击按钮向服务端发送消息

运行结果

在这里插入图片描述

在这里插入图片描述

完结,撒花

相关内容

热门资讯

浑源县检察院公益诉讼快速检测实... 本报讯 近日,浑源县人民检察院公益诉讼快速检测实验室正式投入使用,标志着该院公益诉讼检察工作迈入“科...
专注拆迁业务,靠谱律师助您维权... 在拆迁业务领域,选择一位靠谱、专业的律师至关重要。拆迁过程涉及复杂的法律程序和利益关系,稍有不慎就可...
好友半夜入室作案致三童死亡后自... 12月22日,邝女士向红星新闻反映,她的三名未成年子女于本月初在家中遭人杀害,嫌疑人系其好友李某某。...
靖国神社被韩籍遇难者遗属起诉,... 据环球时报12月25日综合报道,二战期间被日军强制征兵的部分韩籍遇难者遗属23日向首尔中央地方法院提...
今年已为635名用户提供法律服... 近年来,随着互联网的飞速发展,网络空间以其开放性和互动性,极大地丰富了用户的生活方式,成为大众获取信...
泰柬冲突升级,特朗普劝和无效,... 泰柬边境的战事持续升级,尽管特朗普积极介入调停,但他个人的曝光度并未能改变局势。泰国凭借其强大的军力...
山西省生态环境保护条例自202... 山西省人民代表大会常务委员会公告 (第六十五号) 《山西省生态环境保护条例》已由山西省第十四届人民代...
公安部通报金融领域“黑灰产”违... 12月25日,公安部在京召开专题新闻发布会,通报公安部和国家金融监督管理总局联合部署开展金融领域“黑...
涉案金额近300亿!两部门集群... 公安部25日通报公安部和国家金融监督管理总局联合部署开展金融领域“黑灰产”违法犯罪集群打击情况。聚焦...
岚县公安:多元共治解纠纷 本报讯 近期,岚县公安局社科派出所积极推进“进村入户大走访”专项行动,推动警务下沉、关口前移,联动乡...