7.Flink数据流API编程指南-上

目录

概述

Flink中的数据流程序是在数据流上实现转换的常规程序(例如,过滤,更新状态,定义窗口,聚合)。数据流由(例如,消息队列、套接字流、文件)创建的。结果通过接收器返回,例如,接收器可以将数据写入文件或标准输出(例如命令行终端)。Flink程序可以在各种上下文中运行,可以独立运行,也可以嵌入到其他程序中。可以在本地的 jvm 中执行,也可以在多台机器组成的集群中执行。

什么是 DataStream

DataStream API 的名称来自用于表示Flink程序中的数据集合的特殊 DataStream 类。可以将它们视为包含重复项的不可变数据集合。这些数据可以是有界的,也可以是无界的,用于处理它们的 API 是相同的,即流批一体的概念。

在使用方面,数据流与常规Java Collection类似,但在一些关键方面有很大不同。它们是不可变的,一旦创建了它们,就不能添加或删除元素。不仅遍历其中的元素,还可以使用DataStream API操作(也称为转换)对它们进行处理。

可以通过在Flink程序中添加源来创建初始数据流。然后,可以从中派生新的流,并通过使用map、filter等API方法将它们组合起来。

Flink常规编程规范

Flink程序是转换数据流的常规程序。每个程序都由相同的基本部分组成:

  • 1,获取执行环境;
  • 2.加载/创建初始数据,
  • 3.指定对该数据的转换,
  • 4.指定把计算结果存放在哪里,
  • 5.触发程序执行

现在,将对这些步骤进行概述,有关详细信息,请参阅相应的部分。注意,Java DataStream API的所有核心类都可以在 org.apache.flink.streaming.api 中找到。

StreamExecutionEnvironment是所有Flink程序的基础。你可以在StreamExecutionEnvironment上使用这些静态方法获得一个:

java 复制代码
getExecutionEnvironment();

createLocalEnvironment();

createRemoteEnvironment(String host, int port, String... jarFiles);

通常,只需要使用 getExecutionEnvironment() ,因为它将根据上下文做出正确选择:如果在IDE中执行程序或作为常规Java程序,它将创建一个本地环境,将在本地机器上执行程序。如果将程序打包成一个JAR文件,并通过命令行调用它,那么Flink集群管理器将执行程序的主方法,getExecutionEnvironment()将返回一个执行环境,用于在集群上执行程序。

为了指定数据源,执行环境有几种方法可以使用各种方法从文件中读取:可以将它们作为CSV文件逐行读取,也可以使用任何其他提供的源。要将文本文件作为行序列读取,可以使用:

java 复制代码
final StreamExecutionEnvironment env = StreamExecutionEnvironment.getExecutionEnvironment();

DataStream<String> text = env.readTextFile("file:///path/to/file");

这将提供一个数据流,然后可以在其上应用转换以创建新的派生数据流。

通过调用带有转换函数的DataStream上的方法来应用转换。例如,一个map应用如下:

java 复制代码
DataStream<String> input = ...;

DataStream<Integer> parsed = input.map(new MapFunction<String, Integer>() {
    @Override
    public Integer map(String value) {
        return Integer.parseInt(value);
    }
});

这将原始集合中的每个String转换为Integer来创建一个新的数据流。

一旦有了包含最终结果的数据流,就可以通过创建接收器将其写入外部系统。这些只是一些创建接收器的示例方法:

java 复制代码
writeAsText(String path);

print();

上面的步骤完成时,就需要通过调用StreamExecutionEnvironment上的execute()来触发程序执行。根据ExecutionEnvironment的类型,在自己的机器上执行,或者将程序提交到集群上执行。

execute()方法将等待作业完成,然后返回jobeexecutionresult,其中包含执行时间和累加器结果。

如果不想等待作业完成,可以通过调用StreamExecutionEnvironment上的executeAsync()来触发异步作业执行。它将返回一个JobClient,可以使用它与刚刚提交的作业进行通信。例如,下面是如何通过使用executeAsync()来实现execute()的语义。

java 复制代码
final JobClient jobClient = env.executeAsync();

final JobExecutionResult jobExecutionResult = jobClient.getJobExecutionResult().get();

关于程序执行的最后一部分对于理解何时以及如何执行Flink操作至关重要。所有Flink程序都是惰性执行的:当程序的main方法被执行时,数据加载和转换不会直接发生。相反,每个操作都被创建并添加到数据流图中。当执行环境中的execute()调用显式触发执行时,操作才会实际执行。程序是在本地执行还是在集群上执行取决于执行环境的类型。

惰性计算可以构建复杂的程序,Flink将这些程序作为一个整体规划单元执行。

编程案例

下面是一个Flink批处理案例,代表了Flink流批处理的基本流程。

java 复制代码
import org.apache.flink.streaming.api.environment.StreamExecutionEnvironment;
import org.apache.flink.streaming.api.datastream.DataStream;
import org.apache.flink.api.common.functions.FilterFunction;

public class Example {

    public static void main(String[] args) throws Exception {
        final StreamExecutionEnvironment env =
                StreamExecutionEnvironment.getExecutionEnvironment();

        DataStream<Person> flintstones = env.fromElements(
                new Person("Fred", 35),
                new Person("Wilma", 35),
                new Person("Pebbles", 2));

        DataStream<Person> adults = flintstones.filter(new FilterFunction<Person>() {
            @Override
            public boolean filter(Person person) throws Exception {
                return person.age >= 18;
            }
        });

        adults.print();

        env.execute();
    }

    public static class Person {
        public String name;
        public Integer age;

        public Person(String name, Integer age) {
            this.name = name;
            this.age = age;
        }

        public String toString() {
            return this.name + ": age " + this.age.toString();
        }
    }
}

数据源

源是程序读取输入的地方。可以使用 StreamExecutionEnvironment.addSource(sourceFunction) 将源附加到程序中。Flink附带了许多预实现的源代码函数,可以通过为非并行源代码实现 SourceFunction ,或者通过实现 ParallelSourceFunction 接口或为并行源代码扩展 RichParallelSourceFunction 来编写自己的自定义源代码。

有几个预定义的流源可以从 StreamExecutionEnvironment 中访问

基于文件

  • readTextFile(path) -逐行读取文本文件,即遵守TextInputFormat规范的文件,并将其作为字符串返回。
  • readFile(fileInputFormat, path) -按照指定的文件输入格式读取(一次)文件。
  • readFile(fileInputFormat, path, watchType, interval, pathFilter, typeInfo) -这是前两个方法在内部调用的方法。它根据给定的fileInputFormat读取路径中的文件。根据所提供的watchType,这个源可以定期(每隔毫秒)监视新数据的路径(fileprocessingmode . process_continuous),或者处理一次当前路径中的数据并退出(FileProcessingMode.PROCESS_ONCE)。使用pathFilter,用户可以进一步排除正在处理的文件。

Socket-based

socketTextStream - 从 socket 中读取,元素之间使用分隔器

Collection-based:

fromCollection(Collection) - 通过Java Java.util.Collection创建数据流,所有集合中的元素是同一种类型。

fromCollection(Iterator, Class) - 通过iterator创建数据流,通过 Class 指定返回 iterator 返回数据的类型

fromElements(T ...) - Creates a data stream from the given sequence of objects. All objects must be of the same type.

fromParallelCollection(SplittableIterator, Class) - Creates a data stream from an iterator, in parallel. The class specifies the data type of the elements returned by the iterator.

fromSequence(from, to) - Generates the sequence of numbers in the given interval, in parallel.

自定义

结束

下部分在下一篇中补充。

相关推荐
杰克逊的日记6 小时前
Flink运维要点
大数据·运维·flink
张伯毅12 小时前
Flink SQL 将kafka topic的数据写到另外一个topic里面
sql·flink·kafka
菜鸟冲锋号14 小时前
Flink SQL、Hudi 、Doris在数据上的组合应用
大数据·flink
maozexijr18 小时前
Flink 的任务槽和槽共享
大数据·flink
强哥叨逼叨2 天前
没经过我同意,flink window就把数据存到state里的了?
大数据·flink
董可伦3 天前
Dinky 安装部署并配置提交 Flink Yarn 任务
android·adb·flink
千叶真尹6 天前
基于Flink的用户画像 OLAP 实时数仓统计分析
flink
从头再来的码农8 天前
大数据Flink相关面试题(一)
大数据·flink
MarkHD8 天前
第四天 从CAN总线到Spark/Flink实时处理
大数据·flink·spark
SparkSql9 天前
FlinkCDC采集MySQL8.4报错
大数据·flink