技术选型:为何批处理咱们却选择了Flink

最近接手了一个改造多平台日志服务的需求,通过梳理,我认为以前服务在设计上存在缺陷。通过一段时间的技术方案调研,最终咱们决定选择使用 Flink 重构该服务。html

目前重构后的服务已成功经受了国庆节流量洪峰的考验,今日特来总结回顾,和你们分享一下经验。sql

业务需求及背景

在了解改造服务的需求前,咱们首先要明确,要解决什么问题以及目前的服务是如何解决的。数据库

当前的业务逻辑仍是比较清晰的:编程

  • 采集同一时段不一样数据源的日志;
  • 对采集的数据进行处理;
  • 将处理后的数据上传到指定位置,供客户下载。

咱们面临的痛点和难点:网络

  • 日志的数据量比较大:每小时未压缩的日志数据量有 50 多个 G,节假日等特殊时间节点,日志量会翻倍。
  • 目前服务使用单机进行处理,速度比较慢,扩容不方便。
  • 目前服务处理数据时须要清洗字段,按时间排序,统计某字段的频率等步骤。这些步骤都属于 ETL 中的常规操做,可是目前是以代码的形式实现的,咱们想以配置形式减小重复编码,尽可能更加简单、通用。

方案1:咱们须要一个数据库吗?

针对以上业务需求,有同窗提出:“咱们能够把全部原始数据放到数据库中,后续的 ETL 能够经过 SQL 实现。”架构

若是你一听到"数据库"想到的就是 Pg、Mysql、Oracle 等,以为这个方案不具备可行性,那你就错了。数据库的类型和维度是很是丰富的,以下图所示:dom

数据库行业全景图

按业务负载特征,关系型数据库可分为 OLTP 数据库(交易型)和 OLAP 数据库(分析型) :编程语言

  • OLTP,Online Transaction Processing。OLTP 数据库最大的特色是支持事务,增删查改等功能强大,适合须要被频繁修改的"热数据"。咱们耳熟能详的 Mysql、Pg 等都属于这一类。缺点就是因为支持事务,插入时比较慢。拿来实现咱们的需求显然是不合适的。
  • OLAP,Online Analytical Processing,数据分析为主。不支持事务,或者说是对事务的支持有限。OLAP 的场景是:大多数是读请求,数据老是以至关大的批(> 1000 rows)进行写入,不修改已添加的数据。

方案 1 小结函数式编程

OLAP 的使用场景符合咱们的需求,为此咱们还专门去调研了一下 ClickHouse。可是有一个因素让咱们最终放弃了使用 OLAP。请注意,数据库存储的数据都是二维的,有行和列两个维度。可是日志只有行一个维度。若是说为了把日志存入数据库把每行日志都切分,那统计字段的需求也就顺手实现了,又何须存到数据呢?函数

因此,OLAP 使用场景隐含的一个特色是:存入的数据须要被多维度反复分析的。这样才有把数据存入数据库的动力,像咱们当前的需求对日志进行简单的变形后仍旧以文本日志的形式输出,使用 OLAP 是不合适的。

方案2:Hive 为何不行?

看到这,熟悉大数据的同窗可能会以为咱们水平很 Low,由于业务需求归根到底就是三个字:批处理。

那咱们为何第一时间没有考虑上大数据呢?

大数据处理流程

大数据确实如雷贯耳,但如今咱们的日志处理这块大部分都是用 Golang 实现的,团队内的其余业务用了 Python、Lua、C,就是没有用过到 Java。而目前大数据都是基于 JVM 开发的。Golang 调用这些服务没有一个好用的客户端。

因此基于团队目前的技术储备,大数据才没有成为咱们的首选。可是从目前的情况来看大数据是最优解了。那么咱们该选用大数据的什么组件实现需求呢?

放弃使用数据库直接使用 HDFS 存储日志文件,应该是毋庸置疑的。

咱们需求是离线批处理数据,对时效性没有要求,MapReduce 和 Hive 都能知足需求。可是 MapReduce 与 Hive 相比,Hive 在 MapReduce 上作了一层封装而且支持 SQL。看起来 Hive 是很是合适的。

那为何最终放弃了 Hive 呢?

  • 机器资源问题。公司其余团队已经有一套 HDFS 的设施,只用来作存储,Hadoop 的 MapReduce 这个组件根本没跑起来。那套 HDFS 部署的机器资源比较紧张,他们担忧咱们使用 MapReduce 和 Hive 跑计算,会影响如今 HDFS 的性能; 咱们想审批一批新的机器,从新使用 Ambari 搭建一套 Hadoop,却被告知没那么多闲置的机器资源。并且咱们即使申请下来了机器,只跑目前服务也跑不满,机器资源大部分也会被闲置,也有浪费资源的嫌疑。
  • 存储分离是趋势。在调研中咱们发现,像 Hadoop 这样把存储和计算放到一块儿的已经比较"落伍"了。Hadoop 存储分离,须要修改源码,目前没有开源实现,只是云厂商和各个大数据公司有相关商业产品。从这个角度讲,即使咱们本身搞定了机器资源搭一套 Hadoop,也只不过是拾人牙慧罢了。

大数据生态图

方案 2 小结

再合适的技术方案不能落地也是空谈。可是技术方案想要落地时,已经不是一个单纯的技术问题了,资源限制,团队限制等都须要考虑在内。

一个优秀的技术方案立足于解决当下的问题,而且能放眼将来勾画蓝图,这样你们以为 "有利可图",才愿意跟你一块儿折腾。

方案3:为何咱们放弃了 Spark?

通用的计算引擎

虽然使用 HDFS 的团队不同意在他们的机器上跑 Hive,可是咱们把日志数据存到他们的 HDFS 上仍是没问题的。在已知 "存储和分离是趋势" 是前提的基础下,"咱们到底须要什么" 这个问题已经有答案了。

咱们须要的是一个通用的计算引擎。存储已经剥离给 HDFS 了,因此咱们只须要找一个工具,帮咱们处理 ETL 就能够了。Spark 和 Flink 正是这样的场景。

Spark 与 Flink 初次交锋

Spark 和 Flink 之间,咱们坚决果断地选择了 Spark。缘由很是简单:

  • Spark 适合批处理。Spark 当初的设计目标就是用来替换 MapReduce。而 Spark 流处理的能力是后来加上去的。因此用 Spark 进行批处理,可谓驾轻就熟。
  • Spark 成熟度高。Spark 目前已经发布到 3.0,而 Flink 尚在 Flink 1.x 阶段。Flink 向来以流处理闻名,虽然被国内某云收购后开始鼓吹 "流批一体",可是线上效果仍是有待检验的。
  • Scala 的加持。Spark 大部分是用 Scala 实现的。Scala 是一门多范式的编程语言,而且与 Haskell 有很深的渊源。Haskell 是一门大名鼎鼎的函数式编程语言。对于函数式编程语言,想必大多数程序猿都有一种 "虽不能至,然心向往之" 的情结。如今使用 Spark 能捎带着耍一耍函数式编程语言 Scala,岂不妙哉?

Scala

挥泪斩 Spark

前文已经交代过了,咱们否决掉 Hive 的一个重要因素是没有足够的机器资源。因此咱们把 Spark 直接部署到云平台上。

对于我司的云平台要补充一些细节。

咱们的云平台是基于 K8S 二次开发的,目前还在迭代当中,所以"Spark on K8S" 的运行模式咱们暂时用不了。在这样的状况下,咱们采用了 "Spark Standalone" 的模式。Standalone 模式,也就是Master Slaver 模式,相似于 Nginx 那样的架构,Master 节点负责接收分发任务,Slaver 节点负责"干活"。

等到咱们在云平台上以 "Spark Standalone" 模式部署好了,跑了几个测试 Case 发现了新问题。咱们的云平台与办公网络是隔离的,若是办公网络想访问云平台的某个 Docker 容器,须要配置域名。而 Spark 的管理页面上不少 URL 的 domain 是所在机器的 IP,容器的 IP 是虚拟 IP,容器重启后IP 就会改变。具体如图:

部署在云平台的 spark

Spark 的管理平台很是重要,由于能从这上面看到当前各个节点运行状况,任务的异常信息等,如今不少连接不能访问,不利于咱们对 Spark 任务进行问题排查和调优。基于这个缘由,咱们最终放弃了 Spark。

方案 3 小结

Spark 你真的很优秀,擅长批处理,如此成熟,还有函数式的基因 。。。这些优势早让我倾心不已。

Spark 你真的是个好人,若是不是云平台的限制,我必定选择你。

Spark,对不起。

方案4:Flink,真香!

给 Spark 发无缺人卡后,咱们看一看新欢 Flink。不客气的说,Flink 初期时不少实现都是抄的 Spark,因此两者的不少概念类似。因此 Flink 一样有 Standalone 模式,咱们在部署阶段没遇到任何问题。

在跑了几个 Flink 测试 Case 后,咱们由衷的感叹 Flink 真香。

放弃 Spark 时咱们的痛点在于 "部署在云平台上的 Spark 服务的管理界面不少功能没法使用",而 Flink 的管理平台彻底没有这个问题。除此以外,Flink 管理平台的 "颜值" 和功能都是 Spark 没法比拟的。

管理平台颜值对比

Spark管理平台页面

Flink管理平台页面

对比之下,Spark 的页面彻底是个"黄脸婆"。

Flink 管理平台功能

因为 Spark 的功能不少不能使用,因此就不重点和 Flink 作比较了。这里只说 Flink 几个让人眼前一亮的功能。

  • 完善的 Restful API

部署了 Flink 或 Spark 服务后,该如何下发计算任务呢? 通常是经过 bin 目录下的一个名称中包含 submit 的可执行程序。那若是想把 Flink 或 Spark 作成微服务,经过 http 接口去下发任务呢?

Spark1.0 的时候支持 http,2.0时这个功能基本上废掉了,不少参数不支持了,把 http 这个功能交由 jobService 一个第三方开源组件去实现。这个 jobService 的开源组件对云平台的支持也很是不友好。因此在咱们看来,Spark 经过 Http 下发任务的路子基本被堵死了。

反观 Flink,管理平台的接口是 Restful 的,不只支持 Http 下发计算任务,还能够经过相关接口查看任务状态和获取异常或返回值。

  • 强大的任务分析能力

Flink 的任务分为几个不一样的阶段,每一个不一样的阶段有不一样的颜色。这样仅从颜色就能够判断出当前 Flink 任务执行的大体状况。以下图:

Flink管理平台页面

在任务详情页面,会有任务分解图和任务执行耗时表格,这两个结合起来可以知道固然 Flink 任务是如何分解的,是否出现数据倾斜的状况,哪一个步骤耗时最多,是否有优化的空间。

管理平台页面

这就是作批处理技术选型时候的心路历程,随笔记了下来,但愿对你们有所帮助。

推荐阅读

如何选择适合本身网站的防盗链

HTTP/3 来了,你了解它么?

相关文章
相关标签/搜索