问小白 wenxiaobai
资讯
历史
科技
环境与自然
成长
游戏
财经
文学与艺术
美食
健康
家居
文化
情感
汽车
三农
军事
旅行
运动
教育
生活
星座命理

Hudi、Iceberg和Delta Lake:数据湖表格式对比

创作时间:
作者:
@小白创作中心

Hudi、Iceberg和Delta Lake:数据湖表格式对比

引用
1
来源
1.
https://www.imooc.com/article/323303

在构建数据湖时,选择合适的数据存储格式至关重要。Apache Hudi、Apache Iceberg和Delta Lake是目前最受欢迎的三种数据湖表格式。本文将从平台兼容性、更新性能、并发保证等多个维度对这三种格式进行详细对比分析,帮助读者选择最适合其应用场景的数据湖表格式。

平台兼容性

Hudi

Hudi最初由Uber开源,旨在支持列式数据格式的增量更新。它支持从多个来源摄取数据,主要支持Apache Spark和Apache Flink。此外,Hudi还提供了一个基于Spark的实用程序,可以从外部来源读取Apache Kafka。

Hudi支持从Apache Hive、Apache Impala和PrestoDB读取数据。还有一个专门的工具,可以将Hudi表架构同步到Hive Metastore。

Iceberg

Iceberg最初由Netflix开源,旨在解决在S3上存储大型Hive分区数据集时出现的性能、可扩展性和可管理性挑战。

Iceberg支持Apache Spark,适用于读取和写入,包括Spark的结构化流。对于具有有限支持删除的读取,还支持Trino(prestosql)。阅读和写入支持Apache Flink。最后,IceBerge为Apache Hive提供读取支持。

Delta Lake

Delta Lake由Databricks(Apache Spark的创造者)作为一个开源项目维护,提供与读写Spark的深度集成。

使用Hive的SymlinkTextInputFormat可用于Presto、AWS Athena、AWS Redshift Spectrum和Snowflake提供读取支持。虽然这需要导出每个增量表分区的Symlink.txt文件,并且当您可能怀疑时,可以保持较大的表格昂贵。

更新性能和吞吐量

支持大量不变对象的行级更新,可以通过多种方式完成,每个都可以通过其唯一的性能和吞吐量进行替换。让我们来看看每个数据格式采用Upsert操作的策略。我们还将涉及与读取性能有关的其他优化。

Hudi

Hudi表在处理Upsert时的性能权衡中是灵活的(和显式)。两种不同类型的Hudi表之间的权衡差异:

  • 写入表中的复制 - 更新:专门写入Columarar Parquet文件的,创建新对象。这增加了写入成本,但将读取放大降低到零,使其成为读重工作负载的理想选择。
  • 读取表格合并 - 更新:在基于行的日志文件中立即写入,并定期合并到Columpar Parquet中。有趣的是,查询可以包括最新的日志文件数据,提供有用的旋钮,供用户选择数据延迟和查询效率。

Hudi通过利用主键索引来有效地跟踪包含陈旧记录的文件,进一步优化了Upsert操作。

Iceberg

通过去年夏天的Spark 3.0发布,Iceberg支持Upserts通过合并融入查询。他们使用直接的复制方式工作,其中包含需要更新的记录的文件立即重写。

Iceberg 擅长读性能与包含大量分区的表。通过将Mappest文件维护地图对象进行分区并保留列级别统计信息,iceBerg避免昂贵的对象存储目录列表或需要从Hive获取分区数据。

此外,iceBerg的清单允许同时分配单个文件到多个分区。这使得Iceberg表在分区修剪中有效,提高了高度选择性查询的延迟。

Delta Lake

在合并操作期间,Delta使用元数据通知的数据跳过来对文件进行分类,以便为需要数据插入、更新或删除。然后,它执行这些操作,并将其记录为称为Delta日志的JSON日志文件中的“提交”。这些日志文件每10个提交文件重写为镶木条“检查点”文件,该文件保存表的整个状态以防止昂贵的日志文件遍历。

为了保持性能,Delta表需要进行定期的压缩过程,占用许多小地形文件并将它们组合成更少的更大的文件(最佳?1GB,但大小至少128MB)。Delta Engine,DataBricks的专有版本,支持自动触发此过程的自动压缩,以及其他后面的幕后写优化。

Delta Engine通过使用过滤器提供键索引,订购在读取时间,本地缓存等更好的文件修剪中,通过提供键索引来提高性能。

并发保证

允许数据表的就地更新意味着处理并发性。如果有人在更新时读取表格,会发生什么?当多个作家同时产生冲突的变化时会发生什么?

通常,数据库通过多数并发控制(MVCC)来解决此问题,该方法利用逻辑事务日志,其中附加所有更改。另一种称为乐观并发控制(OCC)的方法允许多个写入同时发生,仅在最终提交之前检查冲突。如果检测到冲突,则会重试其中一个事务,直到它成功。

Hudi

真实表,HUDI提供MVCC和OCC并发控制。

Hudi具有MVCC意味着所有写入必须在其中央日志中完全下订购。为了提供此保证,Hudi限制将并发写入1,这意味着只有在给定时间点的表格中只能有一个写入者。

为了防止这种限制,Hudi现在也在实验上提供。此功能需要Apache zookeeper或Hive Metastore来锁定单个文件并提供隔离。

Iceberg

iceberg表通过在更新期间通过在元数据文件上执行原子交换操作来支持乐观的并发性(OCC)。

每次写作的方法都会创建一个新表“快照”。然后,编写者在保持当前快照ID的特殊值上尝试比较和交换(CAS)操作。如果在提交期间没有其他WRITER替换快照,则操作成功。如果另一个作者与此同时进行提交,则其他作者将必须重试直至成功。

在诸如HDF的分布式文件系统上,这可以自然地完成。对于S3,需要一个附加组件来存储指针(当前仅支持Hive Metastore)。

Delta Lake

Delta文档解释说,它使用乐观控制来处理并发性,因为大多数数据湖操作将数据附加到时间有序分区并且不会冲突。

在两个进程添加提交到Delta日志文件的情况下,Delta将“默默地和无缝”检查文件是否更改重叠并允许两者都能在可能的情况下成功。

但是,涉及底层对象存储需要一种提供CAS操作的方式或者当多个编写者开始覆盖彼此的日志条目时失败的方式。

与Iceberg类似,此功能在HDFS上可能出于框中,但不支持S3。因此,在AWS上的AWS上不支持从多个Spark群集的编写,具有真正的事务保证。

注意:专有的Delta Engine版本使用Databricks本身管理的外部同步服务器支持S3上的多集群写入。

那么哪一个适合你?

如果你这么走了,我们已经了解了Apache Hudi、Delta Lake和Apache冰山之间的一些重要相似之处和差异。时间来决定哪种格式对您的用例最有意义!我的推荐是对的,其中场景最适用:

  • 如果您的主要疼痛点并不改变现有记录,而是管理对象存储上的巨大表的元数据负担(超过10k分区)。采用iceBerg将缓解与S3对象列表或Hive Metastore分区枚举相关的性能问题。相反,对缺失和突变的支持仍然是初步的,并且数据保留有涉及的运营开销。
  • 如果您可以使用各种查询引擎,并需要灵活地管理突变数据集。注意到支持工具和整体开发人员体验可以在边缘周围粗糙。尽管可能,但还需要安装和调整Hudi,以实现实际,大规模生产工作负载所需的开销。如果您使用的AWS托管服务,如Athena,Glue或EMR - Hudi已经预装和配置了,并且由AWS支持。
  • 如果您主要是一个Spark Store,期待相对较低的写吞吐量。如果您已经是DataBricks客户,Delta发动机会对读写性能和并发性带来显著的改进,并且可以在生态系统上逐渐下降。对于其他Apache Spark发行版,重要的是要理解Delta Lake,而在开源时,可能会始终落后于Delta Engine以充当产品差异化器。

与LakeFS一体化

如果您想知道“我可以使用Lakefs与这些数据格式一起使用吗?”…答案是肯定的!Lakefs可以与Delta、Iceberg 或Hudi中的任何一个符合,提供了在任何数量的表中分支、合并、回滚等的能力。由于这些格式在表级运行,因此它们不提供跨越多个操作的保证。使用LakeFS,可以在单个隔离分支上修改多个表,然后将这些更改原子变为主分支,实现跨表一致性。

这篇文章是由Paul Singman,Developer Advocate在Lakefs贡献的。

© 2023 北京元石科技有限公司 ◎ 京公网安备 11010802042949号