RPC原理与实现|青训营笔记

52 阅读4分钟

这是我参与「第五届青训营 」笔记创作活动的第15天

本篇文章主要对RPC的基本概念、分层设计以及关键指标进行了总结和分析。

1.RPC基本概念

首先以一个本地函数代码调用的例子进行导入

func main(){
    var a = 2
    var b = 3
    result := calculate(a,b)
    fmt.Println(result)
    return
}

func calculate(x,y int) {
    z := x*y
    return z
}
  • 将a和b的值压栈

  • 通过函数指针找到calculate函数,进入函数取出栈中的值2和3,将其赋予x和y

  • 计算x * y,并将结果存在z

  • 将z的值压栈,然后从calculate返回

  • 从栈中取出z返回值,并赋值给result

对于远程函数调用,RPC需要解决的问题有三个,分别为:函数映射、数据转换成字节流、网络传输

一次RPC完整的过程,如下:

  • IDL文件:IDL通过一种中立的方式来描述接口,使得在不同平台上运行的对象和用不同语言编写的程序可以相互通信

  • 生成代码:通过编译器工具把IDL文件转换成语言对应的静态库

  • 编译码:从内存中表示到字节序列的转换称为编码,反之为解码,也常叫做序列化和反序列化

  • 通信协议:规范了数据在网络中的传输内容和格式。除必须的请求/相应数据外,通常还会包含额外的元数据

  • 网络传输:通常基于成熟的网络库走TCP/UDP传输

对于RPC的优势和缺点:

优势:

  1. 单一职责,有利分工协作金额运维开发

  2. 可扩展性强,资源使用率更优

  3. 故障隔离,服务的整体可靠性更高

缺点:

  1. 服务宕机

  2. 调用过程中发生网络异常

  3. 请求量突增导致服务无法及时处理

2.RPA分层设计

2.1 编解码层-数据格式

语言特定的格式

许多编程语言都内建了将内存对象编码为字节序列的支持,例如Java有java.io.Seralizable

文本格式

JSON、XML、CSV等文本格式,具有人类可读性

二进制编码

具备跨语言和高性能等优点,常见有Thrift的BinaryProtocol,Protobuf等

2.2 编解码层-二进制编码

  • TLV 编码

  • Tag:标签,可以理解为类型

  • Lenght:长度

  • Value:值,Value也可以是个TLV结构

struct Person {
   1: required string       userName,
   2: optional i64          favoriteNumber,  
   3: optional list<string> interests
}

2.3 编解码层-选型

  • 兼容性:支持自动增加新的字段,而不影响老的服务,这将提高系统的灵活度

  • 通用性:支持跨平台、跨语言

  • 性能:从空间和时间两个维度来考虑,也就是编码后数据大小和编码耗费时长

2.4 协议层-概念

  • 特殊结束符:一个特殊字符作为每个协议单元结束的标示

  • 变长协议:以定长加不定长的部分组成,其中定长的部分需要描述不定长的内容长度

2.5 协议层-协议构造

LENGTH:数据包大小,不包含自身

HEADER MAGIC:标识版本信息,协议解析时候快速校验

SEQUENCE NUMBER:表示数据包的seqID,可用于多路复用,单连接内递增

HEADER SIZE:头部长度,从第14个字节开始计算一直到PAYLOAD前

PROTOCOL ID:编解码方式,有Binary和Compact两种

TRANSFORM ID:压缩方式,如zlib和snappy

INFO ID: 传递一些定制的meta信息

PAYLOAD:消息体

2.6 网络通信层-网络库

  • 提供易用API:封装底层Socket API;连接管理和事件分发

  • 功能:协议支持:tcp、udp和uds等;优雅退出、异常处理等

  • 性能:应用层buffer减少copy;高性能定时器、对象池等

3.RPA关键指标

3.1 稳定性-保障策略

  • 熔断:保护调用方,防止被调用的服务出现问题而影响到整个链路

  • 限流:保护被调用方,防止大流量把服务压垮

  • 超时控制:避免浪费资源在不可用节点上

3.2 易用性

开箱即用:合理的默认参数选项、丰富的文档

周边工具:生成代码工具、脚手架工具

简单易用的命令行工具

  • 生成服务代码脚手架

  • 支持protobuf和thrift

  • 内置功能丰富的选项

  • 支持自定义的生成代码插件

3.3 扩展性

Middleware Option 编解码层 协议层 网络传输层 代码生成工具插件扩展

3.4 观测性

Log、Metric、Tracing

内置观测性服务

3.5 高性能

  • 场景:单机多机、单连接多连接、单/多cline 单/多server、不同大小的请求包、不同请求类型:例如pingpong、streaming等

  • 目标:高吞吐、低延迟

  • 手段:连接池、多路复用、高性能编解码协议、高性能网络库

4.总结

本篇文章主要从RPC的相关概念和原理进行介绍和讲解,收获很多,扩展了自己的知识体系,将来可以进行巩固和温习。

5.引用

文章内容主要来自于字节内部课程。