摘要:本文由美团研究员、实时计算负责人鞠大升分享,主要介绍 Flink 助力美团数仓增量生产的应用实践。内容包括:
数仓增量生产
流式数据集成
流式数据处理
流式 OLAP 应用
未来规划
Tips:点击文末「阅读原文」即可回顾作者原版分享视频~
先介绍一下美团数仓的架构以及增量生产。如下图所示,这是美团数仓的简单架构,我把它叫做三横四纵。所谓三横,第一是贯穿全链路的元数据以及血缘,贯穿数据集成、数据处理、数据消费、以及数据应用的全过程链路。另外一块贯穿全链路的是数据安全,包括受限域的认证系统、权限系统、整体的审计系统。根据数据的流向,我们把数据处理的过程分为数据集成、数据处理、数据消费、以及数据应用这 4 个阶段。
我们目前在 Flink 上面应用比较广泛的地方,包括从 Kafka 把数据导到 Hive,包括实时的处理,数据导出的过程。今天的分享就集中在这些方面。
美团的 Flink 目前大概有 6000 台左右的物理机,支撑了 3 万左右的作业。我们消费的 Topic 数在 5 万左右,每天的高峰流量在 1.8 亿条每秒这样的水平上。
第一,实时数仓、经营分析、运营分析、实时营销。
第二,推荐、搜索。
第三,风控、系统监控。
第四,安全审计。
接下来我要引入增量生产的概念。离线数仓关注的三块需求,第一个就是时效性。第二个就是质量,产出的数据的质量。第三个就是成本。
关于时效性,有两个更深层次的含义,第一个叫做实时,第二个叫准时。并不是所有的业务需求都是实时的,很多时候我们的需求是准时。比如做经营分析,每天拿到相应的昨天的经营数据情况即可。实时数仓更多的是解决实时方面的需求。
但是在准时这一块,作为一个企业,更希望在准时跟成本之间做一个权衡。
所以,我把数仓的增量生产定义为对离线数仓的
一个关于准时跟成本的权衡。
另外,数仓增量生产解决
比较
好的一个方面是质量,问题能够及时发现。
如下图所示,我们期望做的实际上是第二幅图。我们期望把离线的生产占用的资源降低,但同时希望它的产出时间能够提前一步。
我们来看一下流式数据集成的第一代。当数据量非常小以及库非常少的时候,直接做一个批的传输系统。在每天凌晨的时候把相应的 DB 数据全部 load 一遍,导到数仓里面。这个架构优势是非常简单,易于维护,但是它的缺点也非常明显,对于一些大的 DB 或者大的数据,load 数据的时间可能需要 2~3 个小时,非常影响离线数仓的产出时间。
基于这个架构,我们增加了流式传递的链路,我们会有经过流式传输的采集系统把相应的 Binlog 采集到 Kafka,同时会经过一个 Kafka 2 Hive 的程序把它导入到原始数据,再经过一层 Merge,产出下游需要的 ODS 数据。
数据集成 V2.0 的优势是非常明显的,我们把数据传输的时间放到了 T+0 这一天去做,在第二天的时候只需要去做一次 merge 就可以了。这个时间可能就从 2~3 个小时减少到一个小时了,节省出来的时间是非常可观的。
在形式上,数据集成的第三代架构前面是没什么变化的,因为它本身已经做到了流式的传输。关键是后面 merge 的流程。每天凌晨 merge 一个小时,仍然是非常浪费时间资源的,甚至对于 HDFS 的压力都会非常大。所以在这块,我们就迭代了 HIDI 架构。
我们设计 HIDI,核心的诉求有四点。第一,支持 Flink 引擎读写。第二,通过 MOR 模式支持基于主键的 Upsert/Delete。第三,小文件管理 Compaction。第四,支持 Table Schema。
基于这些考虑,我们来对比一下 HIDI,Hudi 和 Iceberg。
支持基于主键的 Upsert/Delete
支持和 Flink 集成
小文件管理 Compaction
支持基于主键的 Upsert/Delete
小文件管理 Compaction
写入限定 Spark/DeltaStreamer
流读写支持 SparkStreaming
Iceberg 的优势包括: 支持和 Flink 集成。
如下图所示,我们有数据产生,数据集成,ETL 生产三个阶段。把流式数据集成做到 T+0,ETL 的生产就可以提前了,节省了我们的成本。
我们来讲一下 ETL 的增量生产过程。我们的数据从前面进来,到 Kafka 之后,有 Flink 实时,然后到 Kafka,再到事件的服务,甚至到分析的场景中,这是我们自己做的分析链路。
下面是批处理的一个链路,我们通过 Flink 的集成,集成到 HDFS,然后通过 Spark 去做离线生产,再经过 Flink 把它导出到 OLAP 的应用中。在这样的架构中,增量的生产实际上就是下图标记为绿色的部分,我们期望用 Flink 的增量生产的结构去替换掉 Spark。
第一, Flink 的 SQL 的能力要对齐 Spark。
第二, 我们的 Table Format 这一层需要能够支持 Upsert/Delete 这样的主键更新的实时操作。
第三, 我们的 Table Format 能够支持全量和增量的读取。
我们的全量用于查询和修复数据,而我们的增量是用来进行增量的生产。SQL 化是 ETL 增量生产的第一步,今天分享的主要是说我们基于 Flink SQL 做的实时数仓平台对这一块的支持。
如下图所示,这是实时数仓的模型。业界应该都看过这样的一个模型。
实时数仓的平台架构,分为资源层、存储层、引擎层、SQL 层、平台层、还有应用层。在这里重点强调两点。
这是我们数仓平台的一个 Web IDE。在这样的一个 IDE,我们支持了一个 SQL 的建模的过程,支持了 ETL 的开发的能力。
下面看关于流式的导出跟 OLAP 的应用这一块。如下图所示,是异构数据源的同步图。业界有很多开源的产品做这一块。比如说,不同的存储里面,数据总是在其中进行交换。我们的想法是做一个 Datalink 这样的一个中间件,或者是中间的平台。然后我们把 N 对 N 的数据交换的过程,抽象成一个 N 对 1 的交换过程。
异构数据源的第一版是基于 DataX 来做同步的架构。在这套架构里面,包含了工具平台层、调度层、执行层。
工具平台层的任务非常简单,主要是对接用户,配置同步任务,配置调度,运维。
调度层负责的是任务的调度,当然对于任务的状态管理,以及执行机的管理,很多的工作都需要我们自己去做。
在真正的执行层,通过 DataX 的进程,以及 Task 多线程的一个形式,真正执行把数据从源同步到目的地。
在这样的一个架构里面,发现两个核心的问题。第一个问题就是扩展性的问题。开源的单机版的 DataX 是一个单机多线程的模型,当我们需要传输的数据量非常大的时候,单机多线程模型的可扩展性是很大的问题。第二个问题在调度层,我们需要去管理机器、同步的状态、同步的任务,这个工作非常繁琐。当我们的调度执行机发生故障的时候,整个灾备都需要我们单独去做这块的事情。
基于这样的架构,我们把它改成了一个 Flink 的同步的架构。前面不变,还是工具平台层。在原有的架构里面,我们把调度层里面关于任务调度和执行机的管理这一块都交给了 Yarn 去做,这样我们就从中解脱出来了。第二个,我们在调度层里面的任务状态管理可以直接迁移到 cluster 里面去。
基于 Flink 的 Datalink 的架构优势非常明显。
我们看一下基于 Flink 的同步架构的关键设计,这里总结的经验有四点。
第一,避免跨 TaskManager 的 Shuffle,避免不必要的序列化成本;
第二,务必设计脏数据收集旁路和失败反馈机制;
第三,利用 Flink 的 Accumulators 对批任务设计优雅退出机制;
第四,利用 S3 统一管理 Reader/Writer 插件,分布式热加载,提升部署效率。
基于 Flink 我们做了 Datalink 这样的一个数据导出的平台,基于 Datalink 的导出平台做了 OLAP 的生产平台,在这边除了底层的引擎层之外,我们做了平台层。在这上面,我们对于资源、模型、任务、权限,都做了相应的管理,使得我们进行 OLAP 的生产非常快捷。
这是我们的 OLAP 生产的两个截图。一个是对于 OLAP 中的模型的管理,一个是对于 OLAP 中的任务配置的管理。
经过相应的迭代,我们把 Flink 用到了数据集成、数据处理、离线数据的导出,以及 OLAP 生产的过程中。我们期望未来对于流批的处理能够是统一的,希望数据也是流批统一的。我们希望,不管是实时的链路,还是增量处理的链路,在未来数据统一之后,统一用 Flink 处理,达到真正的流批一体。
▼ 关注「Flink 中文社区」,获取更多技术干货 ▼