Uber 的工程团队撰写一篇文章,介绍了他们的大数据平台如何从传统的基于关系型数据库的 ETL 作业演变为基于 Hadoop 和 Spark 的平台。可扩展的摄取模型、标准传输格式和用于增量更新的自定义库是这个平台的关键组件。
Uber 的各个团队使用大数据来预测乘客需求、欺诈检测、地理空间计算以及解决乘客注册流程的瓶颈问题。他们在 2014 年之前开发的初始解决方案基于 MySQL 和 PostgreSQL。那个时候,他们的数据相对较少——几 TB——可以放在这些 RDBMS 中,用户必须知道如何进行跨数据库查询。城市运营团队、数据科学家和分析师以及工程团队在使用这些数据。在进行工程标准化后,他们开始采用Vertica——一个面向列的分析平台——由 Extract-Transform-Load(ETL)作业提供支持。自定义查询服务通过 SQL 提供对数据的访问。数据量开始增长到数十 TB,同时使用这些数据的团队和服务数量也在增长。Uber 在这个阶段面临的主要问题是缺乏水平可扩展性,由于数据生产者和消费者之间缺乏正式模式,导致成本增加和数据丢失。
工程团队在下一阶段采用了 Hadoop,从多个数据存储提取数据而不对数据进行转换。Apache Spark、Apache Hive 和 Presto 作为查询引擎,是整个技术栈的组成部分。Vertica 速度很快,但扩展成本很高,而 Hive 存在的问题恰好相反。使用自定义模式服务将模式和数据存储在一起解决了前一阶段所面临的问题。数据量增长到数十 PB,数据基础设施每天在 10000 个虚拟 CPU 核心上运行 10 万个作业。
尽管具备了水平可扩展性,但仍然遇到了 HDFS 瓶颈。在 HDFS 集群中,NameNode 负责跟踪集群中每个文件的保存位置,并维护目录树。HDFS 针对大型文件的流式访问进行了优化,太多的小文件导致访问效率低下。当他们的数据量超过 10 PB 时,这个问题就出现了。他们通过调整 NameNode 垃圾回收、限制小文件数量和 HDFS 负载管理服务来缓解 HDFS 瓶颈问题。此外,数据无法以最快的速度提供给最终用户。Uber 工程经理 Reza Shiftehfar 写道:
Uber 的业务是实时运行的,因此,我们的服务需要访问尽可能新鲜的数据。为了加速数据交付,我们不得不重新构建我们的管道,以便只提取增量的更新过的和新的数据。
结果出来的是一个叫作Hudi(Hadoop Upserts anD Incrementals)的自定义 Spark 库。它在 HDFS 和 Parquet(存储文件格式)之上构建了一个层,允许更新和删除,从而可以进行增量的 ETL 作业。Hudi 的原理是让用户使用上一个检查点时间戳进行查询,以获取自检查点以来已更新的所有数据,不需要进行全表扫描。这使得模型化数据的延迟从 24 小时缩短到不到一个小时,原始数据的延迟缩短到 30 分钟。
除了 Hudi,Uber 大数据平台最新阶段的另一个组件是通过 Apache Kafka 摄取数据。一个叫作Marmaray的组件从 Kafka 获取数据变更,并使用 Hudi 库将它们推送到 Hadoop。所有这些都是使用 Apache Mesos 和 YARN 编排的。Mesos 适合长期运行的服务,YARN 适合批处理和 Hadoop 作业。Uber 使用了基于 Mesos 构建的自定义调度程序框架Peloton来管理计算工作负载。
查看英文原文:The Evolution of Uber’s 100+ Petabyte Big Data Platform
评论