乐趣区

写给JAVA程序员的机器学习入门-十-应用通信协议如何统一例子

一、接口调用

接口调用如果是远程调用,那么就构成了简单的分布式。最简单的远程接口实现方式是 web service 或 rest。当然一个合理的分布式应用不仅仅是远程接口调用这么简单。还需要有负载均衡、缓存等功能。最简单实现分布式的技术是 Rest 接口,因为 Rest 接口可以使用现存的各种服务器,比如负载均衡服务器和缓存服务器来实现负载均衡和缓存功能。

二、统一通信协议

关于通信协议,不同的公司有不同的选择,但是建议同一公司内部使用统一的通信协议,比较典型的有 grpc 和 brpc。

1. gRPC 简介

gRPC 是 Google 发布的基于 HTTP 2.0 传输层协议承载的高性能开源软件框架,提供了支持多种编程语言的、对网络设备进行配置和纳管的方法。由于是开源框架,通信的双方可以进行二次开发,所以客户端和服务器端之间的通信会更加专注于业务层面的内容,减少了对由 gRPC 框架实现的底层通信的关注。如下图,DATA 部分即业务层面内容,下面所有的信息都由 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 标准设计,带来诸如双向流、流控、头部压缩、单 TCP 连接上的多复用请求等特。这些特性使得其在移动设备上表现更好,更省电和节省空间占用。
关于具体 gRPC 报文的结构,可以参考下图:

下面展示一下 gRPC 的交互过程

  1. 交换机在开启 gRPC 功能后充当 gRPC 客户端的角色,采集服务器充当 gRPC 服务器角色;
  2. 交换机会根据订阅的事件构建对应数据的格式(GPB/JSON),通过 Protocol Buffers 进行编写 proto 文件,交换机与服务器建立 gRPC 通道,通过 gRPC 协议向服务器发送请求消息;
  3. 服务器收到请求消息后,服务器会通过 Protocol Buffers 解译 proto 文件,还原出最先定义好格式的数据结构,进行业务处理;
  4. 数据梳理完后,服务器需要使用 Protocol Buffers 重编译应答数据,通过 gRPC 协议向交换机发送应答消息;
  5. 交换机收到应答消息后,结束本次的 gRPC 交互。

上图展示的是 gRPC 交互过程的具体流程,这也是 Telemetry 触发方式其中之一,称为 Dial-out 模式。简单地说,gRPC 就是在客户端和服务器端开启 gRPC 功能后建立连接,将设备上配置的订阅数据推送给服务器端。

2. brpc

与 grpc 类似,brpc 源自百度,目前支撑百度内部大约 75 万个同时在线的实例。
其实基于以上的几种选择都能够完成高效的开发,团队内部使用统一的标准,这样更有利于模块化和统一标准。
服务间的通信是通过轻量级的 web 服务,使用同步的 REST API 进行通信。在实际的项目应用中,一般推荐在查询的时候使用同步机制,在增删改使用异步的方式,结合消息队列来实现数据的操作,以保证最终的数据一致性。
具体可以使用 BRPC 做如下

  1. 搭建能在一个端口支持多协议的服务, 或访问各种服务
  2. Server 能同步或异步处理请求
  3. Client 支持同步、异步、半同步,或使用组合 channels 简化复杂的分库或并发访问
  4. 通过 http 界面调试服务, 使用 cpu, heap, contention profilers
  5. 获得更好的延时和吞吐
  6. 把你组织中使用的协议快速地加入 brpc,或定制各类组件, 包括命名服务 (dns, zk, etcd), 负载均衡 (rr, random, consistent hashing)

三、rest API

REST API 应为创建、检索、更新和删除操作使用标准 HTTP 动词,而且应特别注意操作是否幂等。
POST 操作可用于创建资源。POST 操作的明显特征是它不是幂等的。举例而言,如果使用 POST 请求创建资源,而且启动该请求多次,那么每次调用后都会创建一个新的唯一资源。
GET 操作必须是幂等的且不会产生意外结果。具体来讲,带有查询参数的 GET 请求不应用于更改或更新信息(而应使用 POST、PUT 或 PATCH)。
PUT 操作可用于更新资源。PUT 操作通常包含要更新的资源的完整副本,使该操作具有幂等性。
PATCH 操作允许对资源执行部分更新。它们不一定是幂等的,具体取决于如何指定增量并应用到资源上。例如,如果一个 PATCH 操作表明一个值应从 A 改为 B,那么它就是幂等的。如果它已启动多次而且值已是 B,则没有任何效果。对 PATCH 操作的支持仍不一致。例如,Java EE7 中的 JAX-RS 中没有 @PATCH 注释。
DELETE 操作用于删除资源。删除操作是幂等的,因为资源只能删除一次。但是,返回代码不同,因为第一次操作将成功 (200),而后续调用不会找到资源 (204)。

四、你们怎么解决

不同项目组之间使用的语言有可能不同,框架有可能不同,同样的,通信协议有可能不同,你们怎么解决的呢?

退出移动版