▲图3Spark集群架构
具体来说,当在集群上执行一个应用时,SparkContext可以连接到集群资源管理器(如YARN),获取集群的Worker Node的Executor,然后将应用程序代码上传到Executor中,再将Task发送给Executor运行。
Spark的核心数据结构是RDD(Resilient Distributed Dataset,弹性分布式数据集),只支持读操作,如需修改,只能通过创建新的RDD实现。
02实时流处理当前实时处理数据的需求越来越多,例如实时统计分析、实时推荐、在线业务反欺诈等。相比批处理模式,流处理不是对整个数据集进行处理,而是实时对每条数据执行相应操作。流处理系统的主要指标有以下几个方面:时延、吞吐量、容错、传输保障(如支持恰好一次)、易扩展性、功能函数丰富性、状态管理(例如窗口数据)等。
目前市面上有很多成熟的开源流处理平台,典型的如Storm、Flink、Spark Streaming。三者的简单对比如下:Storm与Flink都是原生的流处理模型,Spark Streaming是基于Spark实现的微批操作;Spark Streaming的时延相对前两者高;Flink与Streaming的吞吐量高,支持的查询功能与计算函数也比Storm多。总体来说,Flink是这三者中综合性能与功能更好的流平台,当前的社区发展也更火热。
1.Flink简介Flink最初由德国一所大学开发,后进入Apache孵化器,现在已成为最流行的流式数据处理框架。Flink提供准确的大规模流处理,支持高可用,能够7×24小时全天候运行,支持exactly-once语义、支持机器学习,具有高吞吐量和低延迟的优点,可每秒处理数百万个事件,毫秒级延迟,支持具有不同的表现力和灵活性的分层API,支持批流
一体。
2.Flink的架构Flink是一个分布式系统,可以作为独立群集运行,也可以运行在所有常见的集群资源管理器上,例如Hadoop YARN、Apache Mesos和Kubernetes。
Flink采用主从架构,Flink集群的运行程序由两种类型的进程组成:JobManager和一个或多个TaskManager。TaskManager连接到JobManager,通知自己可用,并被安排工作。两者的功能如下所示:
- JobManager负责协调Flink应用程序的分布式执行,完成任务计划、检查点协调、故障恢复协调等工作。高可用性设置需要用到多个JobManager,其中一个作为领导者(leader),其他备用。
- TaskManager,也称为Worker,负责执行数据处理流(dataflow)的任务,并缓冲和交换数据流。TaskManager中资源调度的最小单位是任务槽(slot),TaskManager中slot的数量代表并发处理任务的数量。
Flink架构示意图如图4所示。
▲图4Flink架构
客户端(Client)不是Flink运行程序的一部分,它在给JobManager发送作业后,就可以断开连接或保持连接状态以接收进度报告。
3.Flink对数据的处理方式流处理是对没有边界数据流的处理。执行时,应用程序映射到由流和转换运算符组成的流式数据处理流。这些数据流形成有向图,以一个或多个源(source)开始,以一个或多个输出(sink)结束。程序中的转换与运算符之间通常是一对一的关系,但有时一个转换可以包含多个运算符。Flink流式处理步骤示例如图5所示。
▲图5Flink流式处理步骤示例
4.Flink的接口抽象Flink为开发流、批处理的应用提供了四层抽象,实践中大多数应用程序是基于核心API的DataStream/DataSet API进行编程的,四层抽象从低到高的示意图如图6所示。
▲图6 Flink接口抽象层次
- Low-level: 提供底层的基础构建函数,用户可以注册事件时间和处理时间回调,从而允许程序实现复杂的计算。
- Core API: DataStream API(有界/无界流)和DataSet API(有界数据集)。基于这些API,用户可以实现transformation、join、aggregation、windows、state等形式的数据处理。
- Table API: 基于表(table)的声明性领域特定语言(DSL)。Table API遵循(扩展的)关系模型,表具有附加的表结构(schema),并且该API提供类似关系模型的操作,例如select、join、group-by、aggregate等。Table API的表达性不如Core API,但优点是使用起来更为简洁,编码更少。Flink支持在表和DataStream/DataSet之间进行无缝转换,因此可以将Table API与DataStream/DataSet API混合使用。
- SQL: 此层是最高层的抽象,在语义和表达方式上均类似于Table API,但是将程序表示为SQL查询表达式。