随着数据来源的丰富,数据呈现多出多样化的特点。与此同时,企业对数据分析功能的依赖也在激增,许多企业都在构建或者计划构建自己的数据湖。那先看下什么是数据湖?
Wikipedia定义:
数据湖是一类存储数据自然/原始格式的系统或存储,通常是对象块或者文件。数据湖通常是企业中全量数据的单一存储。全量数据包括原始系统所产生的原始数据拷贝以及为了各类任务而产生的转换数据,各类任务包括报表、可视化、高级分析和机器学习。数据湖中包括来自于关系型数据库中的结构化数据(行和列)、半结构化数据(如CSV、日志、XML、JSON)、非结构化数据(如email、文档、PDF等)和二进制数据(如图像、音频、视频)。
数据湖对存取的数据没有格式类型的限制,数据产生后,可以按照数据的原始内容和属性,直接存储到数据湖,无需在数据上传之前对数据进行任何的结构化处理。数据湖对存储数据的类型提供了充足的灵活性,没有传统“入仓”的各种限制,数据产生后就能从对接的数据通道上传到数据湖,根据实际分析需求,再进行数据抽取(Extract)、转换(Transform)、加载(Load),生产所需要的格式数据,生产的处理后的数据可以再存储到数据湖中,供其他阶段或者分析中使用。
数据湖的典型应用场景包括数据分析和挖掘、机器学习、实时数据分析和监控、数据治理等。
目前常用数据湖组件有Apache Hudi和Apache Iceberg:
Hudi(Hadoop Upserts Deletes and Incrementals), 强调了主要支持Upserts、Deletes和Incremental数据处理。典型用法是将上游数据通过Kafka或Sqoop,经由DeltaStreamer(Hudi 自身提供)写入。DeltaStreamer是一个常驻服务,不断地从上游拉取数据写入。
Hudi表的文件组织形式是在每个分区(Partition)内,数据文件被切分组织成一个个文件组(FileGroup)。Hudi表有主键设计,每条数据通过主健进行唯一标识。
在查询方面,Hudi支持Hive、Spark、Presto。Hudi另一个特点是支持Copy On Write 和Merge On Read。
Iceberg 官网定义为 Apache Iceberg is an open table format for huge analytic datasets “面向海量数据分析场景的开放式表格式”。通过该表格式,将下层的存储介质、文件格式与上层计算引擎进行解耦。
Iceberg 没有像Hudi一样模拟业务数据库的设计模式(主键+索引)来实现数据更新,而是设计了另一种文件组织形式来实现数据的Update操作。
Iceberg文件组织分为四层,分别为Metadata、Snapshot、Manifest、File。
Metadata文件记录了最新的快照信息和历史快照记录。每次Commit都会生成一个Snapshot,是当时表的全局快照,即选定某个快照读取时读到的是全量数据。Snapshot文件记录了历史的Manifest文件和本次Commit新增的Manifest,当进行增量读取时只要指定快照的新增的Manifest就可以实现读取新增的数据。Manifest文件记录了写入的文件与分区的对应关系,并记录了文件中字段的一些统计信息便于快速查找。File即实际写入的数据文件。
在查询方面,Iceberg支持Spark、Presto。Iceberg一个特点是提供了ACID的语义支持,通过Snapshot进行读写分离,所有操作可以保证原子性。
通过基础的分析对比可以看到,两个引擎的设计场景并不完全相同:
Hudi为了Incremental的Upserts;Iceberg定位于高性能的分析与可靠的数据管理。随着技术的演进,两者都在不断补齐自己缺失的能力。
没有最好的技术架构,只有最适合当前业务场景的技术架构。