Rhino 字节跳动全链路压测的实践( 五 )


Rhino 字节跳动全链路压测的实践

文章插图
 
RPC 任务对于 RPC 任务,Rhino 也自动完成了对 IDL 的解析,然后转换成 JSON 格式,便于用户参数化处理 。
Rhino 字节跳动全链路压测的实践

文章插图
 
自定义-Go Plugin对于非 HTTP/RPC 的协议,以及有复杂逻辑的压测任务,Rhino 平台也提供了完善的解决方案——Go Plugin 。
Go Plugin 提供了一种方式,通过在主程序和共享库直接定义一系列的约定或者接口,就可以动态加载其他人编译的 Go 语言共享对象,使得主程序可以在编译后动态加载共享库,实现热插拔的插件系统 。此外主程序和共享库的开发者不需要共享代码,只要双方的约定不变,修改共享库后也不再需要重新编译主程序 。
Rhino 字节跳动全链路压测的实践

文章插图
 
用户只要根据规范要求,实现一段发压业务逻辑代码即可 。Rhino 平台可以自动拉取代码,触发编译 。并将编译后的插件 SO 文件分发到多个压测 Agent 。Agent 动态加载 SO 文件,并发运行起来,就可以达到压测的目的 。此外,Rhino 还针对常见 Go Plugin 压测场景,建立了压测代码示例代码库 。对于压测新手,简单修改下业务逻辑代码,就可以完成压测了 。这样就解决了非常见协议,以及复杂压测场景等的压测问题 。
3.7 压测引擎单 Agent 多引擎压测调度的最小单元是压测 Agent,但是实际每个 Agent 中有挂载多种压测引擎的,来支撑不同的压测场景 。Rhino 平台在压测数据和压测引擎之间增加了一个压测引擎适配层,实现了压测数据与压测引擎的解耦 。压测引擎适配层,会根据选择不同的压测引擎,生成不同 Schema 的压测数据,启用不同的引擎来完成压测,而这些对用户是透明的 。
Rhino 字节跳动全链路压测的实践

文章插图
 
压测引擎在压测引擎上,我们有开源的压测引擎,也有自研的压测引擎 。
开源压测引擎的优点是维护人多,功能比较丰富,稳定且性能好,缺点就是输入格式固定,定制难度大 。此外 Agent 与开源压测引擎之间通常是不同进程,进程通信也存在比较大的问题,不容易控制 。
自研压测引擎,优点是和 Agent 通常运行在单进程内,比较容易控制;缺点可能就是性能稍微差一些 。但是 Golang 天然支持高并发,因此自研和开源之间的性能差距并不明显 。
  • HTTP 协议:默认 Gatling,单机发压性能非常好,远超于 Jmeter 。对于智能压测,或动态调节的情况,会切换到自研压测引擎上 。
  • RPC 协议:自研引擎,主要利用 Golang 协程+RPC 连接池,来完成高并发压测 。
  • GoPlugin 协议:自研引擎,利用 Golang Plugin 可动态装载的特性,自动装载自定义压测插件,来完成压测 。
3.8 压测监控客户端监控由于公司监控系统,最小时间粒度是 30s,30s 内的数据会聚合成一个点 。这个时间粒度对于压测来说是比较难以接受的 。因此,Rhino 平台自己搭建了一套客户端监控系统 。
  • 每个 Request 都会以请求开始时间为基准打一个点 。
  • 单个 Agent 内,会将相同任务相同接口,1s 内的打点数据在本地做一次汇总,上报到 Kafka 中 。
  • 监控服务会消费 Kafka 中的打点数据,将多个 Agent 上报的数据进行再次汇总,然后写入数据库中 。
  • 前端监控报表会实时拉取数据库中监控汇总数据,绘制实时监控曲线
  • 在监控数据汇总流程中,对于请求响应时间的 PCT99 计算,是比较难处理的:目前 Rhino 平台采用的 T-Digest 算法来计算 1 秒内的 PCT99整个时间段内的 PCT99 的计算,则是以 PCT & AGV 的方式聚合 。即单位时间内通过 T-Digest 计算 PCT99;整个时间段内的 PCT99,则是对所有点的 PCT99 取平均值 。整体计算方案已与公司服务端监控算法对齐,目的是减少客户端监控与服务端监控之间的 Gap,减少压测结果分析的干扰因素 。

Rhino 字节跳动全链路压测的实践

文章插图
 
服务端监控服务端监控,直接接入了公司 Metric 系统 。