Apache Flink是一个分布式流处理器,它使用直接且富有表现力的API来实现有状态的流处理应用程序。它以容错的方式高效地大规模运行此类应用程序。Flink于2014年4月加入Apache软件基金会作为孵化项目,并于2015年1月成为顶级项目。从一开始,Flink就有一个非常活跃且不断增长的用户和贡献者的社区。到目前为止,已有超过350人参与了Flink的工作,它已经发展成为最成熟的开源流处理引擎之一,并被广泛采用。Flink在全球不同行业的许多公司和企业中为大型关键业务应用程序提供支持。

流处理不仅为已建立的用例提供了更好的解决方案,而且还促进了新的应用程序、软件架构以及商业机会,因此它正迅速的被大大小小各种规模的公司和企业所采用。在本章中,我们将讨论为什么有状态的流处理变得如此流行,并评估它的潜力。我们首先回顾传统的数据处理应用程序体系结构【 data processing application architectures】,并指出它们的局限性。接下来,我们将介绍基于有状态的流式处理设计的应用程序,与传统的方法相比,该设计具有许多有趣的特性和优点。我们简要讨论开源流处理器的发展,并帮助您在本地Flink实例上运行第一个流应用程序。最后,我们告诉你在阅读这本书的时候你会学到什么。

1.传统的数据基础设施[ Data Infrastructures]

公司会使用许多不同的应用程序来运行它们的业务,例如企业资源规划(ERP)系统、客户关系管理(CRM)软件或基于web的应用程序。所有这些系统通常都为数据处理(应用程序本身)和数据存储(事务性数据库系统)设计了单独的分层,如图1-1所示:

docker flink分流合流 基于apache flink的流处理_Flink

图1-1 传统的应用

应用程序通常连接到外部服务或面向人类用户,并持续处理传入的事件,如订单、邮件或网站点击。在处理事件时,应用程序通过对远程数据库系统运行事务,来读取状态或更新状态。通常,一个数据库系统服务于多个应用程序,这些应用程序甚至常常访问的是相同的库或表

当应用程序需要演变或扩展时,这种设计可能会导致问题。由于多个应用程序可能工作在相同的数据表示【data representation】,或者共享相同的基础设施,因此更改数据库表或扩展数据库系统需要仔细的规划和大量的工作。最近一种克服应用程序紧密捆绑的方法是微服务设计模式。微服务指的是被设计为小型、自包含且独立的应用程序。他们遵循UNIX的哲学------只做一件事,并把它做好。复杂的应用程序是通过将几个微服务相互连接而构建的,这些微服务仅通过诸如RESTful HTTP连接之类的标准化接口进行通信。由于微服务之间是严格解耦的,并且只能通过规范的接口进行通信,因此每个微服务都可以使用自定义技术栈(包括编程语言、库和数据存储)来实现。微服务,及其所有必需的软件和服务,通常被打包/捆绑并部署在独立的容器中。图1-2描述了一个微服务体系结构。

docker flink分流合流 基于apache flink的流处理_docker flink分流合流_02

图1-2 微服务架构
存储在公司各种事务性数据库系统中的数据可以为公司业务的各个方面提供有价值的见解。例如,可以对订单处理系统的数据进行分析,以获得随时间的销售增长、确定延迟发货的原因或预测未来的销售以调整库存。然而,这种事务性数据通常分布在多个分离的的数据库系统之间,当它们可以被联合分析时,事务性数据就会变得更有价值。此外,我们常常需要将数据转换为通用格式。

IT系统中通常使用一个通用组件—数据仓库,来实现这样的需求,而不是直接在事务性数据库上运行分析查询。数据仓库是用于分析查询工作负载(query workloads)的专用数据库系统。为了填充数据仓库,需要将事务性数据库系统所管理的数据复制到数据仓库中。将数据复制到数据仓库的处理过程称为提取-转换-加载(extract-transform-load, ETL)。ETL流程从事务性数据库中提取数据,将其转换为一种通用的表示形式,其中可能包括验证、值规范化、编码、重复数据删除和模式转换,最后将其加载到分析数据库中。ETL处理过程可能非常复杂,通常需要技术复杂的解决方案来满足对于性能的需求。为了使数据仓库的数据保持最新,ETL处理过程需要定期运行。

一旦数据被导入到数据仓库中,它就可以被查询和分析。通常,在数据仓库上执行两类查询。第一种类型是定期/周期性的报告查询【periodic report queries】,用于计算与业务相关的统计信息,如收益、用户增长或产量。这些指标被组成有助于评估业务状况的报告。第二种类型是专门/临时的的查询【ad-hoc queries】,这类查询的目的是为特定问题提供答案,以支持关键业务的决策。这两种查询都由数据仓库以批处理方式执行,即,查询的数据输入是完全可用的,并且查询会在返回计算结果之后终止。图1-3描述了该体系架构。

docker flink分流合流 基于apache flink的流处理_Scala_03

图1-3 用于数据分析的传统的数据仓库

在Apache Hadoop兴起之前,专门的分析数据库系统和数据仓库是数据分析工作负载【 data analytics workloads】的主要解决方案。然而,随着Hadoop的日益普及,企业意识到很多有价值的数据被排除在他们以往的数据分析处理之外。通常,这些数据要么是非结构化的,即不严格遵循关系型模式,或者是过于庞大,无法有效地存储在关系数据库系统中。今天,Apache Hadoop生态系统的组件是许多企业和公司的IIT基础设施中不可或缺的一部分。与将所有数据插入关系型数据库系统不同,而是将大量数据(如日志文件、社交媒体或web点击日志)写入Hadoop的分布式文件系统(HDFS)或其他大容量数据存储(如Apache HBase),它们都以较小的成本提供巨大的存储容量。驻留在此类存储系统中的数据可以被SQL-on-hadoop的引擎访问,例如Apache Hive、Apache Drill或Apache Impala。但是,即使是Hadoop生态系统的存储系统和执行引擎,其基础架构的整体运行模式与传统的数据仓库架构基本相同,即,定期提取数据并将其加载到数据存储中,并以批处理方式处理定期/周期性或专门/临时性查询。

2.有状态流处理【Stateful Stream Processing】

一个重要的观察结果是,几乎所有的数据都是作为连续的事件流创建的。想想用户在网站或移动应用程序中的交互、订单的创建、服务器日志或传感器测量;所有这些数据都是事件流。事实上,很难找到一下子就生成的完整且有限的数据集的例子。有状态的流处理是用于处理无界的事件流的应用程序设计模式,它适用于公司IT基础结构中的许多不同的用例。在讨论它的用例之前,我们简要地解释一下什么是有状态的流处理以及它是如何工作的。

任何处理事件流且不只是执行一次记录的简单转换的应用程序都需要是有状态的,即,具有存储和访问中间数据的能力。当应用程序接收到一个事件时,它可以执行任意的计算,包括从该状态中读取数据或将数据写入状态。原则上,状态可以存储在不同的地方,也可以从不同的地方被访问,这些地方包括程序变量、本地文件、嵌入式或外部数据库。

Apache Flink将应用程序状态本地存储在内存中或嵌入式数据库中,而不是远程数据库中。由于Flink是一个分布式系统,因此需要保护本地状态不受故障影响,以避免在应用程序或机器故障时数据丢失。Flink通过定期将应用程序状态的一致性检查点写入远程持久化存储来保证这一点。状态、状态一致性和Flink的检查点机制将在接下来的章节中详细讨论。图1-4显示了一个有状态的Flink应用程序。

docker flink分流合流 基于apache flink的流处理_Flink_04


图1-4 有状态的流应用程序

有状态的流处理应用程序通常从事件日志中摄取其传入的事件。事件日志负责存储和分发事件流。事件被写入一个持久的(durable)、仅添加(append-only)的日志中,这意味着事件写入的顺序不能更改。被写入到事件日志中的流可以被相同或不同的使用者多次读取。由于日志的仅添加(append-only)属性,事件总是以完全相同的顺序发布给所有消费者。有多个开源的事件系统可以使用,Apache Kafka是最流行的,或者使勇云计算提供商提供的集成服务。

出于多种原因,将在Flink上运行的有状态的流应用程序和事件日志连接起来很有趣。在这种体系架构中,事件日志充当真实数据的来源,因为它可以持久化输入事件,并以确定性的顺序重播它们。在发生故障时,Flink通过先前获取的检查点来恢复有状态的流应用程序的状态,并重置事件日志上的读取位置,从而恢复有状态的流应用程序。应用程序将重放(并快进)来自事件日志的输入事件,直到它到达流的尾部。该技术用于从故障中恢复,但也可以用于更新应用程序、修复bug和修复先前发出的结果、将应用程序迁移到不同的集群或使用不同的应用程序版本执行A /B测试。

如前所述,有状态的流处理是一种通用且灵活的设计模式,可以用于处理许多不同的用例。在接下来的文章中,我们将介绍三类应用程序:

  1. 事件驱动的应用程序
  2. 数据管道应用程序
  3. 数据分析应用程序

这些应用程序通常使用有状态的流处理过程来实现,并给出真实世界应用程序的示例。我们将这些类别描述为不同的模式,以强调有状态流处理的通用性。然而,大多数实际的应用程序都是多个类别的特性的结合体,这再次显示了这种应用设计模式的灵活性。

2.1事件驱动应用程序

事件驱动的应用程序是有状态的流应用程序,它接收事件流并在接收的事件上应用业务逻辑。根据业务逻辑的不同,事件驱动的应用程序可以触发一些操作,比如发送警报或者电子邮件,或者是将事件写入到输出事件流,该输出事件流可能会被其他事件驱动应用程序作为输入事件流而消费。

事件驱动应用程序的典型用例包括:

  • 实时推荐,例如,当顾客浏览零售商的网站时推荐产品
  • 模式检测或复杂事件处理(CEP),例如,用于信用卡交易中的欺诈检测
  • 异常检测,例如,检测侵入计算机网络的企图

事件驱动的应用程序是前面讨论的微服务的演变。它们通过事件日志而不是REST调用进行通信,并将应用程序数据保存为本地状态,而不是将其写入外部数据存储中或是从外部数据存储中读取数据,这类数据存储包括事务性数据库或键值存储。图1-5绘制了一个由事件驱动的流应用程序组成的服务体系结构。

docker flink分流合流 基于apache flink的流处理_docker flink分流合流_05

图1-5 事件驱动应用程序架构
事件驱动的应用程序是一种有趣的设计模式,因为它与传统的独立出存储和计算的分层的体系架构或者目前流行的微服务体系架构相比,它们提供了一些优点。与对远程数据存储进行读写查询相比,本地状态访问,即从内存或本地磁盘进行读写操作,提供了非常好的性能。缩放和容错不需要特别考虑,因为这些方面是由流处理器处理的。最后,通过利用事件日志作为输入源,应用程序的完整输入可以可靠地存储并以确定的顺序重播。这是非常有吸引力的,特别是与Flink的保存点(savepoint)特性相结合,该特性可以将应用程序的状态重置为之前的某一一致性的保存点。通过重置(可能已被修改)应用程序的状态并重播输入事件,可以帮助我们修复应用程序的Bug并纠正/订正其影响,部署新版本的应用程序而不丢失其状态,或者运行what-if或A/B测试。据我们所知,有一家公司决定基于事件日志和事件驱动应用程序构建社交网络的后端,原因就在于这些特性。

事件驱动的应用程序对运行它们的流处理器有很高的要求。业务逻辑受它对状态和时间的控制能力的限制。这个方面取决于流处理器的API、它提供的状态原语的种类,以及它对事件时间处理所支持的质量。此外,唯一状态一致性【 exactly-once state consistency 】以及扩展应用程序的能力,则是最基本的要求。Apache FLink满足所有的这些条件,是运行事件驱动应用程序的一个很好的选择。

2.2数据管道和实时ETL

今天的IT体系结构包括许多不同的数据存储,例如关系和专用数据库系统、事件日志、分布式文件系统、内存缓存和搜索索引。所有这些系统都以不同的表示形式和数据结构存储数据,以便为它们的特定目提供最佳性能。组织/机构的数据的子集存储在多个系统中。例如,网上商城提供的产品信息可以存储在事务性数据库、web缓存和搜索索引中。由于数据的这种复制,数据存储之间必须保持同步。

传统的方法是使用一个定期的ELT,在存储系统之间移动数据,而这种方法通常不能足够快地传播更新。相反,一种常见的方法是将所有的更改写入到作为事实(truth,可以理解为真实数据的意思)数据来源的事件日志中。事件日志将这些更改发布给消费者,这些消费者会将这些更改合并到受影响的数据存储中。根据用例和数据存储,通常在合并之前需要对数据进行处理。例如,需要对它们进行规范化、与额外数据连接起来,或预先聚合,例如:ETL处理过程通常执行的转换。

低延迟的摄入、转换和插入数据是有状态的流处理应用程序的另一个通用使用场景。我们将这种类型的应用程序称为数据管道。数据管道的额外要求是能够在短时间内处理大量数据,即,支持高吞吐量和扩展应用程序的能力。操作数据管道的流处理器还应该支持各种source connector和sink connector,以便与各种存储系统以不同的数据格式进行数据读写操作。同样,Flink提供了操作数据管道所需的所有特性,并包含许多连接器。

2.3流分析

在本章之前,我们描述了数据分析管道的通用体系结构。ETL作业定期将数据导入到数据存储中,而数据则是由专门的查询或定时调度的查询来处理。无论架构是基于数据仓库还是Hadoop生态系统的组件,基本的操作模式—批处理—这都是相同的。虽然将数据定期加载到数据分析系统的方法多年来一直是最先进的,但它有一个明显的缺点。

显然,ETL作业和报告查询的周期性特性导致了相当大的延迟。根据调度间隔的不同,可能需要数小时或数天的时间,才能将某个数据点包括在报告中。在某种程度上,通过使用数据管道程序将数据导入到数据存储,可以减少延迟。然而,即使是连续的ETL,在查询处理事件之前也总会有一定的延迟。在过去,用几个小时甚至几天的延迟来分析数据通常是可以接受的,因为对新结果或见解的迅速响应并没有产生多么显著的优势。然而,在过去的十年里,情况发生了戏剧性的变化。快速数字化和互联系统的出现,使实时收集更多数据并立即对这些数据采取行动成为可能,例如通过调整以适应不断变化的条件或个性化的用户体验。在线零售商可以在用户浏览其网站时向其推荐产品;手机游戏可以给用户赠送虚拟礼物,让他们留在游戏中,或者在适当的时候提供游戏内购买;制造商可以监视机器的行为并触发维护操作以减少生产中断。所有这些用例都需要收集实时数据,并以低延迟进行分析,并立即对结果做出反应。传统的面向批处理的体系结构是无法处理这样的用例。

您可能并不惊讶于有状态的流处理是构建低延迟分析管道的正确技术。流分析应用程序不需要等待周期性触发,而是不断地接收事件流,并通过低延迟的合并最新事件来维护更新结果。这类似于数据库系统用来更新物化视图的视图维护技术。通常,流应用程序将结果存储在支持高效更新的外部数据存储中,例如数据库或键值存储。此外,Flink还提供了一个名为可查询状态【queryable state】的特性,允许用户将应用程序的状态作为键查找表【key-lookup table】公开开来,并允许外部应用程序访问它。流分析应用程序的实时更新结果可用于为仪表板【dashboard】应用程序提供动力,如图1-6所示。

docker flink分流合流 基于apache flink的流处理_Java_06

图1-6 流分析应用程序
除了将事件整合到分析结果中的时间变得要短得多之外,流分析应用程序还有另一个不那么明显的优势。传统的分析管道由几个单独的组件组成,例如ETL处理、存储系统,在基于hadoop的环境中,还包括一个数据处理器和调度器来触发作业或查询。这些组件需要仔细编排,尤其是错误处理和故障恢复可能会变得更有挑战性。

相反,运行有状态流程序的流处理器会负责所有的处理步骤,包括事件摄入、持续计算(包括状态维护)和更新结果。此外,流处理器负责以唯一状态一致性【 exactly-once state consistency】保证从故障中恢复,而且应该能够调整应用程序的并行性。支持流分析应用的额外需求是:一个是支持按照事件时间【event-time】处理事件,即保证事件处理的顺序,以便产生正确和确定的结果,另一个是需要在短时间内处理大量数据的能力,即高吞吐量。Flink为所有这些需求都提供了完美的答案。

流分析应用程序的典型用例是:

  1. 监控手机网络的质量。
  2. 分析移动应用程序中的用户行为。
  3. 以消费者技术实现实时数据的特别分析。
    虽然本书没有涉及,但值得一提的是Flink还提供了对流的SQL查询分析的支持。多家公司已经基于Flink的SQL支持构建了流分析服务,既可以用于内部使用,也可以公开提供给付费用户。

3.开源流处理的演进

数据流处理并不是一种新技术。最早的研究原型和商业产品可以追溯到20世纪90年代末。然而,流处理技术在最近的发展在很大程度上是由成熟的开源流处理器驱动的。今天,分布式开源流处理器为许多企业的关键业务应用程序提供支持,这些应用程序横跨不同的行业,如(在线)零售、社交媒体、电信、游戏和银行。开源软件是这一趋势的主要驱动力,主要有两个原因:

  1. 开源流处理软件是一种人人都可以评估和使用的商品。
  2. 由于许多开源社区的努力,可扩展的流处理技术正在迅速成熟和发展
    仅Apache软件基金会就有十多个与流处理相关的项目。新的分布式流处理项目正不断地进入开源阶段,并以新的特性和功能挑战最先进的技术。这些新来者的特性通常被更早一代的流处理器所采用。此外,开源软件的用户更是新特性的发起者或者贡献者。通过这种方式,开源社区不断改进其项目的能力,并进一步推动流处理的技术边界。我们将简要回顾过去,看看开源流处理的前世今生。

第一代分布式开源流处理器得到了广泛的采用,而主要的关注点落在毫秒级延迟的事件处理,以及提供了在发生故障时不会丢失事件的保证。这些系统具有相当底层的API,并且没有为流应用程序提供具有准确性和一致性的结果的内置支持,因为结果取决于事件到达的时间和顺序。此外,即使事件不会在失败的情况下丢失,它们也可以被多次处理。与保证准确结果的批处理程序相反,第一批开源流处理器用结果的准确性换取了更好的延迟。数据处理系统(实时的)可以提供快速或准确的结果,这导致了图1-7所示的所谓的Lambda体系结构的设计。

docker flink分流合流 基于apache flink的流处理_docker flink分流合流_07

图1-7 Lambda架构
Lambda体系架构通过一个由低延迟流处理器支持的速度层[Speed Layer],扩展了传统的周期性的批处理体系结构。到达Lambda体系架构的数据被流处理器消化,并被写入批处理存储器(如HDFS)。流处理器在接近实时的情况下计算出可能不准确的结果,并将结果写入速度表【speed table】。写入到批处理存储器的数据由批处理程序定期的处理。并将准确的结果写入批处理表【batch table】中,删除速度表中相应的不准确结果。应用程序通过合并来自速度表【speed table】中的最新但仅是近似的结果和来自batch表的更老但准确的结果来使用服务层【Service Layer】的结果。Lambda体系结构旨在改善原始批处理分析体系架构的过高的结果延迟。然而,这种方法有一些明显的缺点。首先,它需要两个语义等效的应用程序逻辑实现,用于两个具有不同api的独立处理系统。其次,流处理器计算的最新结果并不准确,只是近似。第三,Lambda体系结构很难设置和维护。教科书式的设置是由流处理器、批处理器、速度存储、批存储和用于接收批处理器数据和调度批作业的工具组成。

下一代分布式开源流处理器在第一代的基础上进行了改进,提供了更好的故障保证,并确保在出现故障时,每条记录只对结果贡献一次。此外,编程API从相当低级的操作符接口发展到具有更多内置原语的高级API。然而,一些改进,如更高的吞吐量和更好的故障保证,是以将处理延迟从毫秒增加到秒的为代价的。此外,结果仍然取决于事件到达的时间和顺序,即,结果不仅依赖于数据,还依赖于硬件利用率等外部条件。

第三代分布式开源流处理器修复了结果对事件到达的时间和顺序的依赖关系。与唯一失败【 exactly-once failure】的语义相结合,这一代系统是第一个能够计算一致和准确结果的开源流处理器。通过只基于实际真实数据计算结果,这些系统也能够以与处理“实时”数据相同的方式来处理历史数据,即数据一旦被产出,就会立马被摄入。另一个改进是消除了延迟–吞吐量权衡的分解。虽然以前的流处理器只能提供高吞吐量或低延迟,但是第三代的系统能够同时满足这两个方面的需求。这一代的流处理器使得lambda体系结构过时了。

除了到目前为止讨论的系统特性(如容错、性能和结果精度)之外,流处理器还不断添加新的操作特性。由于流应用程序通常需要24/7运行,且停机时间最少,因此许多流处理器增加了一些特性,如高可用设置、与资源管理器(如YARN或Mesos)的紧密集成以及动态扩展流应用程序的能力。其他特性包括支持升级应用程序代码或将作业迁移到不同的集群或流处理器的新版本,而不会丢失应用程序的当前状态。

4.Flink浅尝

Apache Flink是第三代分布式流处理器,具有许多充满竞争力的特性集。它提供精确的流处理,具有高吞吐量和低延迟。特别值得一提的是,以下功能让它脱颖而出:

  • Flink支持事件时间【event-time】和处理事件【processing-time】语义。事件时间【event-time】提供了一致和准确的结果,即使事件顺序被打乱。处理事件【processing-time】适用于对延迟要求非常低的应用程序。
  • Flink支持唯一状态一致性【exactly-once state consistency】保证。
  • Flink实现了毫秒延迟,并且能够每秒处理数百万个事件。Flink应用程序可以扩展到在数千个核心上运行。
  • Flink具有层次化的API,在表达性和易用性方面各不相同。本书涵盖了DataStream API,以及ProcessFunction,这些函数为常见的流处理操作(如窗口操作和异步操作)提供了原语,还包括精确控制状态和时间的接口。Flink的关系型APIs, SQL 以及 LINQ-style Table API在本书中没有讨论。
  • Flink为最常用的存储系统(如Apache Kafka、Apache Cassandra、Elasticsearch、JDBC、Kinesis和(分布式)文件系统(如HDFS和S3)提供了连接器。
  • Flink能够24/7地运行流应用程序,由于它的高可用性设置(没有单点故障)、与YARN和Apache Mesos的紧密集成、从故障中快速恢复以及动态缩放作业的能力,因此几乎不需要停机。
  • Flink允许更新作业的应用程序代码,并将作业迁移到不同的Flink集群,而不会丢失应用程序的状态。
  • 详细和可定制的系统和应用程序度量集合有助于提前识别和响应问题。
  • 最后,Flink也是一个成熟的批处理程序。

除了这些特性之外,Flink由于其易于使用的API,是一个非常适合开发人员的框架。嵌入式执行模式将Flink应用程序作为单个JVM进程启动,该JVM进程可用于在IDE中运行和调试Flink作业。这个特性在开发和测试Flink应用程序时非常有用。

接下来,我们将引导您完成启动本地集群和执行第一个流应用程序的过程,以便让您对Flink有一个初步印象。我们将要运行的应用程序对随机生成的温度传感器读数按时间进行转换和聚合。为此,您的系统需要安装Java 8(或更高版本)。我们将描述UNIX环境的步骤。如果您正在运行Windows,我们建议您使用Linux、Cygwin(用于Windows的Linux环境)或Windows子系统来设置虚拟机,这些子系统是在Windows 10中引入的。

  1. 访问Apache Flink的网页flink.apache.org,下载适用于Scala 2.12的无hadoop二进制版Apache Flink 1.7.1。
  2. 解压 : tar xvfz flink-1.7.1-bin-scala_2.12.tgz
  3. 启动flink本地节点
$ cd flink-1.7.1
$ ./bin/start-cluster.sh
Starting cluster.
Starting standalonesession daemon on host xxx.
Starting taskexecutor daemon on host xxx.
  1. 在浏览器中输入URL http://localhost:8081打开web仪表板。如图1-8所示,您将看到关于刚刚启动的本地Flink集群的一些统计数据。它将显示一个被连接的任务管理器(Flink的工作进程),一个可用的任务槽(由任务管理器提供的资源单元)。
  2. docker flink分流合流 基于apache flink的流处理_Flink_08

  3. 图1-8 Apache Flink的web仪表板的屏幕截图显示概述。
  4. 下载包含本书所有示例程序的JAR文件。
wget https://streaming-with-flink.github.io/examples/download/examples-scala.jar
注意:您还可以按照存储库的README文件上的步骤自己构建JAR文件。
  1. 通过指定应用程序条目类和JAR文件,在本地集群上运行示例:
$ ./bin/flink run \
  -c io.github.streamingwithflink.chapter1.AverageSensorReadings \
  examples-scala.jar
Starting execution of program
Job has been submitted with JobID cfde9dbe315ce162444c475a08cf93d9
  1. 检查web仪表板。您应该看到在“Running Jobs”下面列出运行中的作业。如果单击该作业,您将看到关于运行中的作业的操作的数据流和实时度量,如图1-9所示。
  2. docker flink分流合流 基于apache flink的流处理_Java_09

  3. 图1-9 Apache Flink的web仪表板屏幕截图,显示一个正在运行的作业。
  4. 作业的输出被写入Flink的工作进程的标准输出中,该工作进程在默认情况下被重定向到./log文件夹中的一个文件中。您可以使用tail命令来监视不断生成的输出,如下所示:
$ tail -f ./log/flink-<user>-taskexecutor-<n>-<hostname>.out
您应该看到以下代码行被写入文件
SensorReading(sensor_1,1547718199000,35.80018327300259)
SensorReading(sensor_6,1547718199000,15.402984393403084)
SensorReading(sensor_7,1547718199000,6.720945201171228)
SensorReading(sensor_10,1547718199000,38.101067604893444)

输出可以这样读取:SensorReading的第一个字段是一个sensorId,第二个字段自1970-01-01-00:00以来的毫秒,第三个字段是5秒内计算的平均温度。

  1. 因为您正在运行一个流应用程序,所以它将继续持续运行,直到您取消它。您可以通过在web仪表板中选择作业并单击页面顶部的CANCEL按钮来实现这一点。
  2. 最后,应该停止本地Flink集群
$ ./bin/stop-cluster.sh

就是这样。您刚刚安装并启动了第一个本地Flink集群,并运行了第一个Flink DataStream程序!当然,关于Apache Flink的流处理还有很多要学习的地方,这就是本书的内容。

5.你在本书讲学到什么

本书将教会您关于使用Apache Flink进行流处理的所有知识。第2章讨论流处理的基本概念和挑战,第3章Flink讲解用于满足这些需求的系统架构。第4到8章指导您设置开发环境,介绍DataStream API的基础知识,并详细介绍Flink的时间语义和窗口操作符、它与外部系统的连接器以及Flink容错操作符状态。第9章讨论了如何在各种环境中设置和配置Flink集群,最后第10章讨论了如何操作、监视和维护24/7运行的流应用程序。