Flink Sink API
(二)DataStream API
DataStream是Flink编写流处理作业的API。我们前面说过一个完整的Flink处理程序应该包含三部分:数据源(Source)、转换操作(Transformation)、结果接收(Sink)。下面我们从这三部分来看DataStream API。
(五)结果数据接收器(Data sink)
数据经过Flink处理之后,最终结果会写到file、socket、外部系统或者直接打印出来。数据接收器定义在DataStream类下,我们通过addSink()可以来添加一个接收器。同Source,Flink也提供了一些预定义的Data Sink让我们直接使用。
1.写入文本文件
DataStream提供了两个writeAsText重载方法,写入格式会调用写入对象的toString()方法。
- writeAsText(String path):将DataStream数据写入到指定文件。
- writeAsText(String path,WriteMode writeMode):将DataStream数据写入到指定文件,可以通过writeMode来指定如果文件已经存在应该采用什么方式,可以指定OVERWRITE或NO_OVERWRITE。
2.写入CSV文件
DataStream提供了三个写入csv文件的重载方法,对于DataStream中的每个Filed,都会调用其对象的toString()方法作为写入格式。writeAsCsv只能用于元组(Tuple)的DataStream。
writeAsCsv(String path,WriteMode writeMode,String rowDelimiter,String fieldDelimiter)
参数 | 说明 | 实例 |
---|---|---|
path | 写入文件路径 | |
writeMode | 如果写入文件已经存在,采用什么方式处理 | WriteMode.NO_OVERWRITE 或WriteMode.OVERWRITE |
rowDelimiter | 定义行分隔符 | |
fieldDelimiter | 定义列分隔符 |
DataStream提供了两个简易重载方法:
- writeAsCsv(String path):使用"\n"作为行分隔符,使用","作为列分隔符。
- writeAsCsv(String path,WriteMode writeMode):使用"\n"作为行分隔符,使用","作为列分隔符。
3.写入Socket
Flink提供了将DataStream作为字节数组写入Socket的方法,通过SerializationSchema
来指定输出格式。
writeToSocket(String hostName,int port,SerializationSchema<T> schema)
sum.writeToSocket("localhost", 6666, new SerializationSchema<Tuple2<String, Integer>>() { @Override public byte[] serialize(Tuple2<String, Integer> stringIntegerTuple2) { String serialized = stringIntegerTuple2.f0 + "," + stringIntegerTuple2.f1+"\n"; // 将 Tuple2 转换为字符串 return serialized.getBytes(StandardCharsets.UTF_8); // 将字符串转换为字节数组 } });
4.指定输出格式
DataStream提供了自定义文件输出的类和方法,我们能够自定义对象到字节的转换。
writeUsingOutputFormat(OutputFormat<T> format)
5.结果打印
DataStream提供了print和printToErr打印标准输出/标准错误流。DataStream中的每个元素都会调用其toString()方法作为输出格式,我们也可以指定一个前缀字符来区分不同的输出。
- print():标准输出
- print(String sinkIdentifier):指定输出前缀
- printToErr():标准错误输出
- printToErr(String sinkIdentifier):指定输出前缀
对于并行度大于1的输出,输出结果也将输出任务的标识符作为前缀。
6.自定义输出器
我们一般会自定义输出器,通过实现SinkFunction
接口,然后通过DataStream.addSink(sinkFunction)
来指定数据接收器。
addSink(SinkFunction<T> sinkFunction)
注意:对于DataStream中的writeXxx()方法一般都是用于测试使用,因为他们并没有参与chaeckpoint,所以它们只有"at-last-once"也就是至少处理一次语义。
如果想要可靠输出,想要使用"exactly-once"语义准确将结果写入到文件系统中,我们需要使用flink-connector-filesystem
。此外,我们也可以通过addSink()自定义输出器来使用Flink的checkpoint来完成"exactl-oncey"语义。