Fork me on GitHub

gRPC-Web正式发布

 

前言:

    gRPC-Web是一个JavaScript客户端库,可以使Web应用程序直接与后端gRPC服务进行通信,而无需HTTP服务器充当中介。

这意味着可以通过使用.proto文件定义客户端和服务器端数据类型和服务接口,轻松构建真正的端到端gRPC应用程序体系结构。因此,gRPC-Web为Web开发的整个REST范例提供了一种引人注目的新替代方案。

 

基础:

    gRPC-Web能够使用.protodefinitions和自动生成客户端JavaScript在客户端Web应用程序和后端gRPC服务器之间定义服务“契约”(可以在Closure编译器JavaScript或更广泛使用的CommonJS之间进行选择)。

可以放弃开发过程:创建自定义JSON序列化和反序列化逻辑,处理HTTP状态代码(可能因​​REST API而异),内容类型协商等。从更广泛的架构角度来看,gRPC-Web使端到端gRPC成为可能。下图说明了这一点:

    在左侧的gRPC-Web Universe中,客户端应用程序向GRPC后端服务器说出协议缓冲区,该服务器向其他gRPC后端服务说出协议缓冲区。

    在右侧的REST Universe中,Web应用程序将HTTP发送到后端REST API服务器,然后该服务器将协议缓冲区称为后端服务。需要明确的是,REST应用程序本身没有任何问题。

使用REST API服务器构建了大量非常成功的应用程序,这些服务器使用非HTTP协议与后端服务进行通信。但是想象一下,这些应用程序的开发过程围绕着一个协议和一组.proto接口(以及一组服务契约),几乎可以感受到无数小时的节省和头痛的避免。

gRPC-Web的好处不仅仅是“技术”;他们也是组织的。明亮的橙色线不仅仅是一个不同的协议 - 它是一个独立的工作和认知负荷来源,现在可以很容易地变成亮绿色。

 

使用gRPC-Web的优点:

    随着时间的推移,gRPC-Web将提供更广泛的功能集。但可以看到它从一开始就提供了一些重大胜利:端到端gRPC - 如上所述,使用gRPC-Web,可以正式从堆栈中删除REST组件并将其替换为纯gRPC,能够使用Protocol Buffers创建整个RPC管道。想象一下客户端请求转到HTTP服务器的情况,然后HTTP服务器与5个后端gRPC服务进行交互。将花费尽可能多的时间来构建HTTP交互层,因为将构建整个管道的其余部分。前端和后端团队之间更紧密的协调 - 回想上面的图表。使用Protocol Buffers定义整个RPC管道,不再需要将“微服务团队”与“客户团队”一起使用。客户端 - 后端交互只是一个gRPC层。老实说,还没有完全掌握端到端测试,服务网格集成,持续集成/交付等方面的影响。轻松生成客户端库 - 使用gRPC-Web,与“外部”世界交互的服务器,即连接后端堆栈和互联网的隔膜,现在是gRPC服务器而不是HTTP服务器,这意味着所有服务都是客户端库可以是gRPC库。需要Ruby,Python,Java和其他4种语言的客户端库吗?不再需要为所有这些客户端编写HTTP客户端。

 

一个gRPC-Web示例:

    一个简单的TODO应用程序。在gRPC-Web中,可以从一个简单的todos.proto定义开始,如下所示:

 

     syntax = “proto3”;
      
     package todos;
      
     message Todo {
       string content = 1;
       bool finished = 2;
     }
      
     message GetTodoRequest {
       int32 id = 1;
     }
      
     service TodoService {
       rpc GetTodoById (GetTodoRequest) returns (Todo);
     }

 

  Tip: 可以在GitHub看rawtodos.proto

 

    可以使用该.proto定义使用protoc命令行工具生成CommonJS客户端代码:

    protoc echo.proto \
     --js_out=import_style=commonjs:./output \
     --grpc-web_out=import_style=commonjs:./output

Tip: 可以在GitHub看rawprotoc-gen.sh

    现在从后端gRPC服务器获取TODO列表可以这么简单:

     const {GetTodoRequest} = require(‘./todos_pb.js’);
      
     const {TodoServiceClient} = require(‘./todos_grpc_web_pb.js’);
      
     const todoService = new proto.todos.TodoServiceClient(‘http://localhost:8080’);
     const todoId = 1234;
      
     var getTodoRequest = new proto.todos.GetTodoRequest();
      
     getTodoRequest.setId(todoId);
      
     var metadata = {};
      
     var getTodo = todoService.getTodoById(getTodoRequest, metadata, (err, response) => {
      
       if (err) {
         console.log(err);
       } else {
       const todo = response.todo();
      
       if (todo == null) {
         console.log(`A TODO with the ID ${todoId} wasn’t found`);
       } else {
         console.log(`Fetched TODO with ID ${todoId}: ${todo.content()}`);
       }
     }
     });

Tip: 可以在GitHub托管的rawtodo-service.js

    同样,没有HTTP代码或方法,没有JSON解析,没有头协商。声明了数据类型和服务接口,并且gRPC-Web摘录了所有“硬接线”样板,提供了一个干净且人性化的API(基本上与当前用于gRPC API的Node.js相同的API,刚刚转移到客户端)。在后端,gRPC服务器可以用任何支持gRPC的语言编写,包括Go,Java,C ++,Ruby,Node.js等等(请参阅官方gRPC文档中的语言特定文档)。最后一块拼图是服务代理。从一开始,gRPC-Web将支持Envoy作为默认服务代理,它具有内置的envoy.grpc_web过滤器,只需几行复制和配置即可应用。

 

下一步

    gRPC-Web正式发布版本意味着核心构建块已牢固到位,可以在生产Web应用程序中使用。但是gRPC-Web还有很多其他的东西要来。查看官方路线图,了解核心团队在不久的将来所设想的内容。gRPC-Web还存在着一些问题:

1、前端框架集成 - 常用的前端框架如React,Angular和Vue尚未提供对gRPC-Web的官方支持。希望看到这些框架能够支持它,因为每个框架都会从gRPC中受益匪浅。特定于语言的代理支持 - 从GA版本开始,Envoy是gRPC-Web的默认代理,通过特殊模块提供支持。但也很乐意看到特定语言的进程内代理的开发。进程内代理消除了对特殊代理(例如Envoy和nginx)的需求,并且使得使用gRPC-Web变得更加容易。

2、特定于语言的代理支持 - 从GA版本开始,Envoy是gRPC-Web的默认代理,通过特殊模块提供支持。也很乐意看到特定语言的进程内代理的开发。进程内代理消除了对特殊代理(例如Envoy和nginx)的需求,并且使得使用gRPC-Web变得更加容易。

 

结语

    相信gRPC-Web的话题在社区随着时间推移,会越来越活跃。

 

posted @ 2019-05-07 14:07  广东靓仔-啊锋  阅读(2886)  评论(0编辑  收藏  举报