写点什么

LinkedIn 将 Espresso 从 HTTP1.1 迁移到 HTTP2,连接数减少 88%,延迟降低 75%

作者:Rafal Gancarz

  • 2023-12-20
    北京
  • 本文字数:1331 字

    阅读完需:约 4 分钟

LinkedIn 将 Espresso 从 HTTP1.1 迁移到 HTTP2,连接数减少 88%,延迟降低 75%

LinkedIn 将其 Espresso 数据库从 HTTP/1.1 迁移到 HTTP/2,极大 提升 了可伸缩性和性能,减少了连接数量、降低了延迟并缩短了垃圾回收时间。为了获得这些好处,团队不得不优化 Netty 默认的 HTTP/2 栈来满足需求。


LinkedIn 使用 Espresso(构建在 MySQL 之上的文档平台)来存储和提供大部分数据。随着 LinkedIn 平台的有机增长,数据量不断增加,迫使公司不断扩展 Espresso 集群的规模,并进行优化工作,例如为 Espresso 引入 集中式缓存层 或者 采用 Protocol Buffers 进行服务间通信。



Espresso 高层架构(来源:LinkedIn Engineering Blog)


Espresso 的事务栈包括两个主要组件:路由器和存储节点。路由器负责将请求发送到正确的存储节点上,存储节点负责与 MySQL 集群进行交互,并相应地调整数据格式。这些组件之间的通信使用 HTTP 协议,更具体地说是使用了 Netty 框架。随着时间推移,团队发现到 Espresso 集群的规模增长导致可伸缩性下降。


最近增加的 100 个路由器节点导致存储节点内存使用量增加,额外的垃圾回收导致延迟增加了 15%。此外,由于增加了大量的 HTTP/1.1 连接,从连接池中获取连接所需的时间达到了几毫秒。最后,在发生网络事件(如交换机升级)期间,由于达到存储节点的连接限制,重新建立数千个连接可能会导致错误。


LinkedIn 的软件工程师  Abhishek Andhavarapu 解释了 HTTP/1.1 和 HTTP/2 之间的差异,以及这些差异如何影响 Espresso 平台的可伸缩性和性能:


对于路由器与存储层之间的通信,我们早期的方法是使用了 HTTP/1.1,这是一种广泛用于 Web 服务器和客户端之间交互的协议。然而,HTTP/1.1 是基于每个请求连接的,在大规模集群中,这种方法会导致路由器和存储节点之间产生数百万个并发连接。这导致了可伸缩性、弹性和众多与性能相关的障碍。团队决定在进行 HTTP/2 迁移时继续使用 Netty 框架,但很快发现其性能并不理想(比 HTTP/1.1 实现的吞吐量低 45%,延迟高 60% 左右),因此工程师们不得不去解决 HTTP/2 栈的性能瓶颈。在经过一番诊断后,他们确定了两个改进方向:获取连接和处理请求,以及请求的编码 / 解码。


开发人员通过修改几个内部的 Netty 实现细节来增强功能。他们创建了一个可以重复使用已有通道的处理程序,避免为每个请求创建新的处理通道。他们还引入了一个自定义的 EventLoopGroup 实现,可以更均匀地在工作线程之间平衡连接。为了减少获取连接时的上下文切换,团队重新设计了连接池实现,使用了高性能、线程安全的队列。


此外,SSL 处理使用原生的、基于 JNI 的 SSL 引擎进行了优化,并使用自定义的 SSL 初始化逻辑避免了冗长的 DNS 查找延迟。最后,团队通过创建自定义编解码器来优化编码 / 解码性能,编解码器将 HTTP/2 请求封装为 HTTP/1.1 请求,帮助处理 Espresso 使用的许多自定义 HTTP 标头,并禁用了 HPACK 标头压缩。



迁移到 HTTP/2 后延迟减少(来源:LinkedIn Engineering Blog)


团队报告称,在所有这些定制化改进之后,迁移到 HTTP/2 带来了明显的性能改进,相较于 HTTP/1.1,TCP 连接数量减少了 88%,延迟降低了 65% 至 75%,垃圾回收时间减少了 75% 至 81%,获取连接的等待时间从 11 毫秒 降至 0.02 毫秒(改进了 99%)。


英文原文

https://www.infoq.com/news/2023/12/linkedin-espresso-http2/

2023-12-20 08:004188

评论

发布
暂无评论
发现更多内容

好奇心, 优秀软件工程师的内核品质

亚伦碎语

读书感悟 随笔杂谈

区块链目前实际的应用场景汇总

CECBC

区块链技术 去中心化 应用场景

多个maven项目启动顺序

terrytian

maven

十五年后苹果再次变心

池建强

apple 苹果 芯片 wwdc

工作那么久,才知道的 SOLID 设计原则

闻人

架构师 极客大学架构师训练营

LeetCode 655. Print Binary Tree

liu_liu

算法 LeetCode

基于业务表 Binlog 的事件驱动设计

理帆

MySQL 事件驱动 Binlog

【极客大学】【架构师训练营】【第二周】总结:设计原则

NieXY

极客大学架构师训练营

架构师训练营 - 第三周学习总结

清风徐徐

查找算法系列文(一)一文入门二叉树

淡蓝色

Java 数据结构 算法 二叉树

每日一题-翻转字符串里的单词

程序员老王

LeetCode

就餐卡系统架构设计文档

牛珈羽

极客大学架构师训练营

【极客大学】【架构师训练营】【第二周】依赖倒置原则和接口隔离原则

NieXY

极客大学架构师训练营

游戏夜读 | 《老残游记》很有趣

game1night

循序渐进的中台研发

理帆

中台 业务中台

第四周 学习总结

冯凯

辟谣:程序员不配谈恋爱?你错的可以!真相来了

码农神说

程序员 漫画 相亲

【在云端 002】云时代,何以安放我的个人数据

Bora.Don

云计算 云存储

ARTS Week5

丽子

别兜售你自己不会购买的东西

Neco.W

创业 销售管理 销售

wee1作业总结

牛珈羽

极客大学架构师训练营

SpringBean的生命周期

编号94530

Java spring Spring Boot 生命周期

MySQL InnoDB存储引擎 - 事务

Axe

centos7 操作

InfoQ_1c4a1f813eb1

RabbitMQ跨机房迁移数据零丢失

心平气和

RabbitMQ 消息队列

Redis系列(三):缓存过期该如何剔除?RDB和AOF又是什么?

z小赵

Java redis 高并发 高并发系统设计

iOS & Android 去马赛克处理

liu_liu

ios android 去马赛克

设计原则与设计模式

dapaul

极客大学架构师训练营

食堂就餐卡系统设计

John

极客大学架构师训练营

线性表(数组、链表、队列、栈)详细总结

淡蓝色

Java 数据结构 算法 链表 线性表

设计模式之单例模式和组合模式

dapaul

极客大学架构师训练营

LinkedIn 将 Espresso 从 HTTP1.1 迁移到 HTTP2,连接数减少 88%,延迟降低 75%_DevOps & 平台工程_InfoQ精选文章