传统方案

传统数据集成方案的痛点

大数据技术的应用可以从海量的用户行为数据中进行挖掘分析,根据分析结果优化平台的服务质量,最终满足用户的需求。大数据分析平台就是将大数据技术应用于教育培训领域,为企业经营提供数据支撑:

  • 建立集团数据仓库,统一集团数据中心,把分散的业务数据进行预先处理和存储。
  • 根据业务分析需要,从海量的用户行为数据中进行挖掘分析,定制多维的数据集合,形成数据集市,供各个场景主题使用。
  • 前端业务数据展示选择和控制,选取合适的前端数据统计、分析结果展示工具。

-

IMG_256

上图为传统数据入仓架构 1.0,主要使用 DataX 或 Sqoop 全量同步到 HDFS,再围绕 Hive 做数仓。

此方案存在诸多缺陷:容易影响业务稳定性,因为每天都需要从业务表里查询数据;天级别的产出导致时效性差,延迟高;如果将调度间隔调成几分钟一次,则会对源库造成非常大的压力;扩展性差,业务规模扩大后极易出现性能瓶颈。

上图为传统数据入仓 2.0 架构。分为实时和离线两条链路,实时链路做增量同步,比如通过 Canal 同步到 Kafka 后再做实时回流;全量同步一般只做一次,与每天的增量在 HDFS 上做定时合并,最后导入到 Hive 数仓里。

此方式只做一次全量同步,因此基本不影响业务稳定性,但是增量同步有定时回流,一般只能保持在小时和天级别,因此它的时效性也比较低。同时,全量与增量两条链路是割裂的,意味着链路多,需要维护的组件也多,系统的可维护性会比较差。

IMG_256

上图为传统 CDC ETL 分析架构。通过 Debezium、Canal 等工具采集 CDC 数据后,写入消息队列,再使用计算引擎做计算清洗,最终传输到下游存储,完成实时数仓、数据湖的构建。

IMG_256

传统 CDC ETL 分析里引入了很多组件比如 Debezium、Canal,都需要部署和维护, Kafka 消息队列集群也需要维护。Debezium 的缺陷在于它虽然支持全量加增量,但它的单并发模型无法很好地应对海量数据场景。而 Canal 只能读增量,需要 DataX 与 Sqoop 配合才能读取全量,相当于需要两条链路,需要维护的组件也增加。因此,传统 CDC ETL 分析的痛点是单并发性能差,全量增量割裂,依赖的组件较多。

优享学教育大数据平台

1.0版本技术架构简要分析

IMG_256

架构 : Debezium 1.8 + Pulsar 2.7.0 + Clickhouse 21.9.4

数据处理流程分析:

  • 数据源

Mysql的数据使用Debezium工具单机同步至Pulsar。

七陌及诸葛智能的数据采用Http的方式同步至Pulsar。

  • 数据处理

中间无处理,数据最终在Clickhouse中进行处理。

  • 数据存储

Clickhouse直接消费Pulsar的数据,写入到Clickhouse中,Clickhouse存储原始数据。

现有架构存在的问题主要如下:

  1. 对于Mysql数据源采用的是Debezium工具,该工具仅能单机部署,只能单并发读取Binlog日志,且全量同步不支持断点续传,传输能力较差,每次服务器重启会对Mysql数据进行全量同步,相当耗时,且生态扩展性不好。
  2. Pulsar作为消息传输系统不建议持久化存储数据,因此数据的持久化存储到了Clickhouse中,因此导致Clickhouse存储的是大量明细数据,会导致Clickhouse变得臃肿。
  3. Pulsar与Clickhouse之间缺少数据的处理过程,如果遇到复杂的业务逻辑,比如数据的拉宽、清洗、转换,该架构是无法胜任的。
  4. Clickhouse单表查询性能强劲,但join性能和并发相对较差,而1.0架构的查询Join操作也是在Clickhouse中进行。Clickhouse运维成本高,扩展性较差,各个节点一致性要求高,语法非标准SQL增加使用成本。
  5. 缺乏数仓分层的概念和支撑,如果后期随着业务的发展,指标的计算可能会比较复杂,因此引入数仓分层是非常有必要的。

优享学教育大数据平台2.0版本逻辑架构

图示 中度可信度描述已自动生成

初步设想是将MySQL数据通过Debezium进入到Kafka。但是存储在Kafka的数据有失效时间,不会存太久的历史数据,这样就必须把维度表持久化到HBase中。并且该架构单并发性能差,依赖组件多,链路长,维护工作量庞大,对系统资源的消耗极大。

我们整体的目标规划是替代kafka,把Hudi作为中间存储,将数仓建设在Hudi之上,并以Flink 作为流批一体计算引擎。

形状 描述已自动生成

最终,我们决定直接通过Flink CDC千表入湖,替换Debezium、kafka组件采集数据,采用Flink sql实时处理,在Hudi中做数仓分层,替代在kafka中做分层处理。并且在该项目中,我们采用Dinky将多表的source进行了合并,实现千表入湖,source的合并也可以避免多个任务通过Flink CDC接MySQL表以及Binlog,对MySQL库的性能造成影响。

最终我们采用的架构2.0如下图

架构 : Mysql 5.7 + Flink CDC 2.2 + Hadoop 3.3.0 + Hive 3.1.2 + Flink 1.14.5 + Hudi 0.11.1 + Doris 1.1.0 + Dinky 0.6.6 + Presto 0.261 + Hue 4.1.0

  • 数据源

Mysql业务数据库

  • 数据采集

使用Flink CDC 2.2作为同步工具,将Mysql数据多并发实时采集传输至存储端

  • 数据存储

使用Hudi存储数据,使用Doris存储DWD层与DWS数据做查询分析

  • 数据计算

实时计算:使用Flink/Flink SQL进行实时数据处理

使用Persto灵活用于离线数据分析

  • 数据分析

使用Doris灵活用于自定义数据分析

  • 大数据平台应用

实时场景:实时报表,业务监控,动态展示大屏

这样做的好处有:

  • Kafka不再担任实时数据仓库存储的中间存储介质,而Hudi存储在HDFS上,可以存储海量数据集;
  • 实时数据仓库中间层可以使用 OLAP 分析引擎查询中间结果数据;
  • 真正意义上的准实时,数据 T+1 延迟的问题得到解决;
  • 读时 Schema 不再需要严格定义 Schema 类型,支持 schema evolution;
  • 支持主键索引,数据查询效率数倍增加,并且支持 ACID 语义,保证数据不重复不丢失;
  • Hudi 具有 Timeline 的功能,可以更多存储数据中间的状态数据,数据完备性更强。

优享学教育大数据平台2.0版本数据流转

数据流转如下图

图示 描述已自动生成

  • 业务数据主要放在业务数据库Mysql两个数据库bxg库和crm库中。
  • Flink CDC通过读取Mysql数据库的Binlog日志(Mysql的Binlog日志完整记录了数据库中的变更,可以把Binlog文件当作流的数据源),实时捕获数据变更,将原始数据通过Dinky千表入湖,同步到Hudi的ODS层,并使用Hudi on Hive 会将ODS层元数据信息自动同步到Hive中,便于管理。
  • 使用Flink SQL将Hudi的ODS层数据拉宽写入到Hudi的DWD层 ,DWD层通过join和轻度聚合进入DWS层,DWS层可直接用于BI报表。
  • 使用Flink SQL将Hudi的DWD和DWS层数据同步到Doris的DWD和DWS层。
  • 最终动态显示大屏连接到Doris的DWS层指标数据,将指标动态显示到大屏上。

未来展望

由于在Hive中查询较慢,故在当前的架构中,我们在Doris中也保存了一份数据便于业务查询。但是这导致Doris和Hudi没有很好的融合,数据冗余存储,所以目前相当于还是两套架构。

在后续Doris即将发布的1.2版本支持数据湖联邦查询,即可以通过外表的方式联邦分析位于Hudi中的数据,在避免数据拷贝的前提下,查询性能大幅提升。我们可以升级为如下架构,Metabase和Hue直接接入Doris进行可视化展示。可以很好的解决了我们现有架构的一些问题。

项目技术选型

流式处理平台

采用Flink CDC作为同步工具

  • 为什么选用Flink CDC 2.2?

2.0架构选用了Flink CDC 2.2作为同步工具,相比较 Debezium,Flink CDC底层封装了Debezium,Flink CDC 2.2解决了Debezium的痛点(详见后续CDC讲解):

  1. 并发读取,全量数据的读取性能可以水平扩展。
  2. 全程无锁,不对线上业务产生锁的风险。
  3. 断点续传,支持全量阶段的 Checkpoint。
  • 对比全量+增量同步的能力:

Debezium仅支持单机部署,Flink CDC 2.2支持分布式架构,多并发能力大大提升作业速度。支持断点续传,无需再为每次服务器重启的全量同步耽误大量时间担忧。

  • 在数据转换 / 数据清洗能力上:

在Flink CDC上操作相当简单,可以通过Flink SQL去操作数据,Debezium等则需要通过脚本或者模板去做,所以用户的使用门槛会比较高。

  • 在生态方面,对下游的一些数据库或者数据源的支持:

Flink CDC下游有丰富的Connector,也支持各种自定义Connector。其架构分布式架构不单纯体现在数据读取能力的水平扩展上,更重要的是在大数据场景下分布式系统接入能力。例如Flink CDC的数据入湖或者入仓的时候,下游通常是分布式的系统,如Hive、HDFS、Iceberg、Hudi等,那么从对接入分布式系统能力上看,Flink CDC的架构能够很好地接入此类系统。

  • 配合Dinky实现千表入湖和千表入仓

在Flink CDC进行多表入Hudi和Doris,使用了Dinky作为实时计算平台,可实现千表入仓入湖。Dinky定义了CDCSOURCE整库同步的语法,该语法和CDAS作用相似,可以直接自动构建一个整库入仓入湖的实时任务,并且对Source进行了合并,不会产生额外的Mysql及网络压力,支持对任意Sink的同步,如Kafka、Doris、Hudi、Jdbc 。

分布式计算平台

分布式计算采用Flink SQL

  • 为什么采用Flink SQL?
  1. Flink 具备统一的框架处理有界和无界两种数据流的能力
  2. 部署灵活,Flink 底层支持多种资源调度器,包括Yarn、Kubernetes 等。Flink 自身带的Standalone的调度器,在部署上也十分灵活。
  3. 极高的可伸缩性,可伸缩性对于分布式系统十分重要,阿里巴巴双11大屏采用Flink 处理海量数据,使用过程中测得Flink 峰值可达17亿条/秒。
  4. 极致的流式处理性能。Flink 相对于Storm 最大的特点是将状态语义完全抽象到框架中,支持本地状态读取,避免了大量网络IO,可以极大提升状态存取的性能。
  5. Flink 是目前开源社区中唯一一套集高吞吐、低延迟、高性能于一身的分布式流式数据处理框架。
  6. 基于轻量级分布式快照(Snapshot/Checkpoints)的容错机制
  7. 支持SavePoint保存点,Flink 通过SavePoints 技术将任务执行的快照保存在存储介质上,当任务重启的时候,可以从事先保存的 SavePoints 恢复原有的计算状态,使得任务继续按照停机之前的状态运行。
  8. Flink SQL开发大大降低了开发难度,易于开发和维护

海量数据存储

使用Hudi 存储原始数据,使用Doris存储实时宽表和聚合数据。

  • 为什么选用Hudi?

数据湖是一个集中式数据存储库,用来存储大量的原始数据,使用平面架构来存储数据。湖仓一体(LakeHouse)是新出现的一种数据架构,它同时吸收了数据仓库和数据湖的优势。直接在用于数据湖的低成本存储上实现与数据仓库中类似的数据结构和数据管理功能。
目前市面上流行的三大开源数据湖方案分别为:Delta Lake、Apache Iceberg和Apache Hudi。与其它两种方案相比,Hudi(Hadoop Update Delete Incremantal)最大的特点是:

  1. Update/Delete记录,Hudi使用细粒度的文件/记录级别索引来支持Update/Delete记录,同时还提供写操作的事务保证。查询会处理最后一个提交的快照,并基于此输出结果。
  2. 变更流,Hudi对获取数据变更提供了一流的支持:可以从给定的时间点获取给定表中已Updated/Inserted/Deleted的所有记录的增量流,并解锁新的查询姿势(类别)。
  • 为什么选用Doris

相比较于Clickhouse,Doris优势:

  1. SQL的标准兼容好,使用成本低,是一个强一致性元数据的系统,导数功能较为完备。
  2. 大宽表和多表查询速度都很快,具备CBO(基于代价)优化器,可以很好应对复杂查询,支持高并发查询。
  3. 弹性伸缩能力要好,支持在线扩缩容,运维成本低。

相较于Doris,Clickhouse则需要做较多工作:

  1. ZooKeeper存在性能瓶颈导致集群规模不能特别大。
  2. 基本无法做到弹性伸缩,纯手工扩缩容工作量巨大且容易出错。
  3. 故障节点的容忍度较低,出现一个节点故障会引发某些操作失败。
  4. 导数需要外部保证数据不重不丢,导数失败需要删了重导。
  5. 元数据需要自己保证各个节点一致性,偶发性的不一致情况较多。
  6. 分布式表和本地表有两套表结构,较多用户难以理解。
  7. 多表Join SQL需要改写和优化,方言较多几乎是不兼容其他引擎的SQL。

总体上说,新框架2.0,解决了1.0框架的痛点问题,且实时性更佳,更好的满足业务需求。

在该架构方案的基础上可以继续实现用户画像、智能推荐、数据挖掘等等,非常容易扩展且不需要修改整体架构,因此具有高度的灵活和可扩展性。

框架软件版本

软件 版本
Mysql 5.7
Java 1.8.0_241
Hadoop 3.3.0
Zookeeper 3.4.6
Hive 3.1.2
Flink 1.14.5
Hudi 0.11.1
Doris 1.1.0
Dinky 0.6.6
Flink CDC 2.2.0
Presto 0.261
Hue 4.1.0

非功能描述

框架版本选型

  • Apache:运维麻烦,组件间兼容性需要自己调研。(一般大厂使用,技术实力雄厚,有专业的运维人员)

  • CDH:国内使用最多的版本,但CM不开源,但其实对中、小公司使用来说没有影响(建议使用)

  • HDP:开源,可以进行二次开发,但是没有CDH稳定,国内使用较少

    资源类型 资源大小 描述
    CPU 32核 CPU是计算机的大脑,是衡量服务器性能的首要指标
    内存 128G Spark计算非常的耗内存,因此使用128G内存的服务器,如果有钱可以提供更大的内存服务器
    硬盘 10T 数据存储的地方,因此数据量越大,硬盘的容量必然更高

技术亮点

  • 使用Flink CDC实现业务数据库Mysql的实时采集,支持多并发读取数据源, 大幅提高同步读取的速度。
  • 使用Flink CDC全量读取阶段全程无锁并支持checkpoint,避免锁库风险,同时支持数据断点续传。针对大数据量的全量同步,避免失败造成全量重新同步。
  • 使用 Flink CDC 去替换传统采集组件和消息队列,简化分析链路,降低维护成本,同时更少的组件也意味着数据时效性能够进一步提高。
  • Flink CDC社区22年4月总结用户用了 Flink CDC 后,遇到的第一个痛点就是需要将 MySQL 的 DDL 手工映射成 Flink 的 DDL。手工映射表结构是比较繁琐的,尤其是当表和字段数非常多的时候,手工映射也容易出错。本项目中解决了该问题,实现了自动帮助用户自动去映射表结构。
  • 本项目解决了Flink CDC整库入湖的挑战。用户主要使用SQL,这就需要为每个表的数据同步链路定义一个 INSERT INTO 语句。假如用户的 MySQL 实例中甚至有上千张的业务表,用户就要写上千个 INSERT INTO 语句。每一个INSERT INTO 任务都会创建至少一个数据库连接,读取一次 Binlog 数据。千表入湖的话就需要上千个连接,上千次的 Binlog 重复读取。这就会对 MySQL 和网络造成很大的压力。本项目通过使用Dinky与Flink CDC结合解决了整库同步,千表入湖、千表入仓对Mysql造成压力的问题。
  • 基于Hudi数据湖,使用Hudi on Hive实现湖仓一体,流批一体,基于Hudi on Hive可实现湖上建仓,实现离线数仓开发。
  • 使用Flink SQL对数据进行ETL,大大降低了实时数仓的开发难度。
  • 使用Doris作为存储平台,同时 Doris拥有强大的查询性能