分类目录归档:技术

Flink 1.10 Native Kubernetes 原理与实践

千呼万唤始出来,在 Kubernetes 如火如荼的今天,Flink 社区终于在 1.10 版本提供了对 Kubernetes 的原生支持,也就是 Native Kubernetes Integration。不过还只是Beta版本,预计会在 1.11 版本里面提供完整的支持。

我们知道,在 Flink 1.9 以及之前的版本里面,如果要在 Kubernetes 上运行 Flink 任务是需要事先指定好需要的 TaskManager(TM) 的个数以及CPU和内存的。这样的问题是:大多数情况下,你在任务启动前根本无法精确的预估这个任务需要多少个TM。如果指定的TM多了,会导致资源浪费;如果指定的TM个数少了,会导致任务调度不起来。本质原因是在 Kubernetes 上运行的 Flink 任务并没有直接向 Kubernetes 集群去申请资源。

Flink 在 1.10 版本完成了Active Kubernetes Integration的第一阶段,支持了 session clusters。后续的第二阶段会提供更完整的支持,如支持 per-job 任务提交,以及基于原生 Kubernetes API 的高可用,支持更多的 Kubernetes 参数如 toleration, label 和 … --> 阅读全文

Flink on Yarn / Kubernetes 原理剖析及实践

本文是我参加 Apache Flink China 社区钉钉群直播的教程(进阶篇 2.4)。我稍作调整后发在个人网站(zhoukaibo.com)上。

文中首先对 Flink 架构进行了概述;其次介绍了Yarn在Flink应用中的原理及实践;再次介绍了Kubernetes在Flink应用中的原理及实践;最后对Flink on Yarn/Kubernetes中存在的一些问题进行了解析。

Flink 架构概览

Flink架构概览–Job

用户通过 DataStream API、DataSet API、SQL 和 Table API 编写 Flink 任务,它会生成一个JobGraph。JobGraph 是由 source、map()、keyBy()/window()/apply() 和 Sink 等算子组成的。当 JobGraph 提交给 Flink 集群后,能够以 Local、Standalone、YarnKubernetes 四种模式运行。

Flink架构概览–JobManager

JobManager的功能主要有:

  • 将 JobGraph 转换成 Execution Graph,最终将 Execution
--> 阅读全文

Apache Flink 客户端操作

本文是我参加 Apache Flink China 社区钉钉群直播的教程(基础篇 1.5)。我稍作调整后发在个人网站(zhoukaibo.com)上。

环境说明

在前面几期的课程里面讲过了Flink开发环境的搭建和应用的部署以及运行,今天的课程主要是讲Flink的客户端操作。本次讲解以实际操作为主。这次课程是基于社区的Flink 1.7.2版本,操作系统是Mac系统,浏览器是Google Chrome浏览器。有关开发环境的准备和集群的部署,请参考前面第三期的内容。

课程概要

如下图所示,Flink提供了丰富的客户端操作来提交任务和与任务进行交互,包括 Flink命令行,Scala Shell,SQL Client,Restful API 和 Web。Flink首先提供的最重要的是命令行,其次是SQL Client用于提交SQL任务的运行,还有就是Scala Shell提交Table API的任务。同时,Flink也提供了Restful服务,用户可以通过http方式进行调用。此外,还有Web的方式可以提交任务。

flink_clients.png

在 flink 安装目录的 bin 目录下面可以看到有 flink, start-scala-shell.sh 和 sql-client.sh 等文件,这些都是客户端操作的入口。

flink_1_7_2.jpg

Flink 客户端操作

Flink命令行

flink 的命令行参数很多,输入 flink -h 能看到完整的说明:

1
➜  flink-1.7.2 bin/flink -h
--> 阅读全文

Java SPI 机制分析及其优缺点

SPI 概述

SPI 全称为(Service Provider Interface),是 JDK 内置的一种服务发现机制。它可以动态的为某个接口寻找服务实现,有点类似 IOC(Inversion of Control)的思想,将装配的控制权移到程序之外,在模块化设计中这个机制尤其重要。

使用 SPI 机制需要在 classpath 下的 META-INF/services/ 目录里创建一个以服务接口命名的文件,这个文件里的内容就是这个接口的具体的实现类。

以 JavaMail 程序为例,协议层只需要定义好邮件发送接口,业务层实现对应的协议如 SMTP, IMAP, POP 就可以了。

JavaMail API

SPI 实例说明

接下来通过一个具体的例子来讲解 SPI 的用法,例子的代码在 github 上可以看到。

例子代码在IDEA中的结构如图:

java-spi-example

(1)首先我们提供一个接口类 IOperation 以及它的两个实现类 PlusOperationImplDivisionOperationImpl,都在 com.zhoukaibo.spi 这个包路径下。

1
2
3
4
5
6
7
8
--> 阅读全文

谈谈流计算中的『Exactly Once』特性

本文翻译自 streaml.io 网站上的一篇博文:“Exactly once is NOT exactly the same” ,分析了流计算系统中常说的『Exactly Once』特性,主要观点是:『精确一次』并不保证是完全一样。

目前市面上使用较多的流计算系统有 Apache Storm,Apache Flink, Heron, Apache Kafka (Kafka Streams) 和 Apache Spark (Spark Streaming)。关于流计算系统有个被广泛讨论的特性是『exactly-once』语义,很多系统宣称已经支持了这一特性。但是,到底什么是『exactly-once』,怎么样才算是实现了『exactly-once』,人们存在很多误解和歧义。接下来我们做下分析。

背景

流处理(有时称为事件处理)可以简单地描述为是对无界数据或事件的连续处理。流或事件处理应用程序可以或多或少地被描述为有向图,并且通常被描述为有向无环图(DAG)。在这样的图中,每个边表示数据或事件流,每个顶点表示运算符,会使用程序中定义的逻辑处理来自相邻边的数据或事件。有两种特殊类型的顶点,通常称为 sources 和 sinks。sources 读取外部数据/事件到应用程序中,而 sinks 通常会收集应用程序生成的结果。下图是流式应用程序的示例。

A typical stream processing topology

流处理引擎通常允许用户指定可靠性模式或处理语义,以指示它将为整个应用程序中的数据处理提供哪些保证。这些保证是有意义的,因为你始终会遇到由于网络,机器等可能导致数据丢失的故障。流处理引擎通常为应用程序提供了三种数据处理语义:最多一次、至少一次和精确一次。

如下是对这些不同处理语义的宽松定义:

最多一次(At-most-once)

这本质上是一『尽力而为』的方法。保证数据或事件最多由应用程序中的所有算子处理一次。 这意味着如果数据在被流应用程序完全处理之前发生丢失,则不会进行其他重试或者重新发送。下图中的例子说明了这种情况。

At-most-once processing semantics

至少一次(At-least-once

应用程序中的所有算子都保证数据或事件至少被处理一次。这通常意味着如果事件在流应用程序完全处理之前丢失,则将从源头重放或重新传输事件。然而,由于事件是可以被重传的,因此一个事件有时会被处理多次,这就是所谓的至少一次

下图的例子描述了这种情况:第一个算子最初未能成功处理事件,然后在重试时成功,接着在第二次重试时也成功了,其实是没有必要的。… --> 阅读全文