flink的watermark机制你学会了吗?
大家好,今天我们来聊一聊flink的Watermark机制。
这也是flink系列的的第一篇文章,如果对flink、大数据感兴趣的小伙伴,记得点个关注呀。
背景
flink作为先进的流水计算引擎,提供了三种时间概念,这对基于时间的流处理应用提供了多种可能。
Event time 指生产设备中每个独立的事件发生的时间,比如用户点击产生的时间。
Process time 指正在执行相关进程的机器的系统时间。
IngestionTime 指事件进入flink的时间。
WaterMark机制主要是用来解决EventTime乱序的情况。从事件的产生、到经过消息中间件、然后经过data source和Operator,在传输的过程中,由于网络传输等原因,会导致EventTime出现乱序,如果只是根据EventTime来决定window的运行,我们不能明确数据是否已经全部到位,所以我们需要有一个机制来保证特定的时间后,必须触发window去执行计算了,这个机制就是Watermark。
定义
WaterMark是一种特殊的时间戳,它会被插入到数据流中,用于表示EventTime小于Watermark的事件全部落入到了相应的窗口中。
如图所示,这是一个窗口大小为5的乱序流。w(5)表示EventTime小于5的数据已经落入相应的窗口。当Watermark大于等于窗口的最大时间戳(即窗口的endTime),就会触发相应窗口的计算。比如W(5)大于等于5,会触发窗口[0,5)的计算。
生成
WaterMark有两种生成方式,分别是Punctuated Watermark(标点水位线)和Periodic Watermark(周期性水位线)。
标点水位线
标点水位线(Punctuated Watermark)是通过数据流中某些特殊标记事件来触发新水位线的生成。这种方式下,窗口的触发与时间无关,而是决定于何时收到标记事件。在实际的生产中Punctuated方式在TPS很高的场景下会产生大量的Watermark在一定程度上对下游算子造成压力,所以只有在实时性要求非常高的场景才会选择Punctuated的方式进行Watermark的生成。
周期性水位线
周期性的(允许一定时间间隔或者达到一定的记录条数)产生一个Watermark。水位线提升的时间间隔是由用户设置的,在两次水位线提升时隔内会有一部分消息流入,用户可以根据这部分数据来计算出新的水位线。在实际的生产中Periodic的方式必须结合时间和积累条数两个维度继续周期性产生Watermark,否则在极端情况下会有很大的延时。
案例
在实际的项目中,主要是使用周期性的水位线,我们可以通过env.getConfig().setAutoWatermarkInterval()设置,默认是200ms。
public class test {
public static void main(String[] args) throws Exception {
StreamExecutionEnvironment env = StreamExecutionEnvironment.getExecutionEnvironment();
env.getConfig().setAutoWatermarkInterval(100);
DataStreamSource<String> inputStream = env.socketTextStream("localhost", 8888);
SerializableTimestampAssigner<String> timestampAssigner =
new SerializableTimestampAssigner<String>(){
@Override
public long extractTimestamp(String element, long recordTimestamp) {
String[] fields = element.split(" ");
Long aLong = new Long(fields[0]);
return aLong * 1000L;
}
};
SingleOutputStreamOperator<Tuple2<String,Long>> result=inputStream.assignTimestampsAndWatermarks(
WatermarkStrategy
.<String>forBoundedOutOfOrderness(Duration.ofSeconds(5))
.withTimestampAssigner(timestampAssigner)
).map(new MapFunction<String, Tuple2<String,Long>>() {
@Override
public Tuple2<String, Long> map(String s) {
return Tuple2.of(s.split(" ")[1],1L);
}
}).keyBy(0)
.window(TumblingEventTimeWindows.of(Time.seconds(10)))
.reduce(new ReduceFunction<Tuple2<String, Long>>() {
@Override
public Tuple2<String, Long> reduce(Tuple2<String, Long> stringLongTuple2, Tuple2<String, Long> t1) throws Exception {
return new Tuple2<>(stringLongTuple2.f0,stringLongTuple2.f1+t1.f1);
}
});
result.print();
env.execute("warter mark test");
}
}
当通过nc -l 8888输入数据
1630312530 java
1630312533 java
1630312536 java
1630312540 java
1630312543 java
1630312538 java
1630312545 java
1630312539 java
1630312550 java
1630312549 java
1630312555 java
输出为:
1> (java,5)
1> (java,4)
当事件“1630312545 java”进入流处理后,生成的Watermark为“W(1630312540)”,大于等于窗口[1630312530,1630312540)的endTime,触发窗口的计算,此时延迟数据“1630312538 java”也会被计算在内,所以会输出“(java,5)”,而事件“1630312539 java”是在Watermark已经触发相应的窗口计算后,才进入流处理中,延迟太久,会被忽略掉。当事件“163031255 java”进入流处理后,生成的Wartermark为W(163031250),触发窗口[163031240,163031250)的计算。
最后
到此为止,我们已经把Watermark机制聊完了,如果喜欢,请点个关注吧。
更多有趣知识,请关注公众号【程序员学长】。我给你准备了上百本学习资料,包括python、java、数据结构和算法等。如果需要,请关注公众号【程序员学长】,回复【资料】,即可得。
你知道的越多,你的思维也就越开阔,我们下期再见。
flink的watermark机制你学会了吗?的更多相关文章
- [白话解析] Flink的Watermark机制
[白话解析] Flink的Watermark机制 0x00 摘要 对于Flink来说,Watermark是个很难绕过去的概念.本文将从整体的思路上来说,运用感性直觉的思考来帮大家梳理Watermark ...
- Flink的时间类型和watermark机制
一FlinkTime类型 有3类时间,分别是数据本身的产生时间.进入Flink系统的时间和被处理的时间,在Flink系统中的数据可以有三种时间属性: Event Time 是每条数据在其生产设备上发生 ...
- [源码解析] 从TimeoutException看Flink的心跳机制
[源码解析] 从TimeoutException看Flink的心跳机制 目录 [源码解析] 从TimeoutException看Flink的心跳机制 0x00 摘要 0x01 缘由 0x02 背景概念 ...
- Flink(八)【Flink的窗口机制】
目录 Flink的窗口机制 1.窗口概述 2.窗口分类 基于时间的窗口 滚动窗口(Tumbling Windows) 滑动窗口(Sliding Windows) 会话窗口(Session Window ...
- Flink Runtime核心机制剖析(转)
本文主要介绍 Flink Runtime 的作业执行的核心机制.本文将首先介绍 Flink Runtime 的整体架构以及 Job 的基本执行流程,然后介绍在这个过程,Flink 是怎么进行资源管理. ...
- Apache Flink - 数据流容错机制
Apache Flink提供了一种容错机制,可以持续恢复数据流应用程序的状态.该机制确保即使出现故障,程序的状态最终也会反映来自数据流的每条记录(只有一次). 从容错和消息处理的语义上(at leas ...
- Flink Window窗口机制
总览 Window 是flink处理无限流的核心,Windows将流拆分为有限大小的"桶",我们可以在其上应用计算. Flink 认为 Batch 是 Streaming 的一个特 ...
- [Flink] Flink的waterMark的通俗理解
导读 Flink 为实时计算提供了三种时间,即事件时间(event time).摄入时间(ingestion time)和处理时间(processing time). 遇到的问题: 假设在一个5秒的T ...
- Flink – process watermark
WindowOperator.processElement 主要的工作,将当前的element的value加到对应的window中, windowState.setCurrentNamespace(w ...
随机推荐
- MySQL问题定位-性能优化之我见
前言 首先任何一个数据库不是独立存在的,也不是凭空想象决定出来的. 数据库的架构离不开应用的场景.所以,为了解决某些深入的问题,首先你得掌握数据库的原理与架构.原理掌握得越深入,越能帮助你定位复杂与隐 ...
- ML - 常用数学符号
关系运算符: ±:\pm ×:\times ÷:\div ∣:\mid ∤:\nmid ⋅:\cdot ∘:\circ ∗:\ast ⨀:\bigodot ⨂:\bigotimes ⨁:\bigopl ...
- CSP-S 2020 初赛
游记 游记个鬼啊跨条街就到了=-= 不分Day反正就一天. 9:30开考,8:30起床. 下雨了,一出宿舍门整个学校全被白色的雾气笼罩.愚以为这是祥瑞之气,昨夜似有麒麟貔貅路过,祝我今日初赛RP++ ...
- jvm源码解读--14 defNewGeneration.cpp gc标记复制之后,进行空间清理
进入Eden()->clean()函数 void EdenSpace::clear(bool mangle_space) { ContiguousSpace::clear(mangle_spac ...
- jquery 对HTML标签的克隆、删除
<table width="100%" class="table_form"> <tr> <td>奖励深度(<a hr ...
- Redis.conf分析
Redis.conf 单位 配置文件对大小写不敏感 # 1k => 1000 bytes # 1kb => 1024 bytes # 1m => 1000000 bytes # 1m ...
- 王者并发课-钻石2:分而治之-如何从原理深入理解ForkJoinPool的快与慢
欢迎来到<王者并发课>,本文是该系列文章中的第25篇,砖石中的第2篇. 在上一篇文章中,我们学习了线程池ThreadPoolExecutor,它通过对任务队列和线程的有效管理实现了对并发任 ...
- .Net Core微服务——Consul(4):主从、集群
延续上一篇的话题继续,顺便放上一篇的传送门:点这里. 集群的必要性 consul本身就是管理集群的,现在还需要给consul搞个集群,这是为啥?因为consul单点也容易挂啊!万一管理集群的consu ...
- Python学习的十个阶段,学完神功大成,对应一下看看你自己在哪个阶段
大家好,我是白云. 今天给大家整理了Python学习的十个阶段内容,看看你现在正处于哪个阶段,想学习的朋友也可以根据这个阶段规划学习. 阶段一:Python基础[ 初入江湖] Linux基础 目标: ...
- MySQL的函数使用
目录 COUNT()函数基本使用 SUM( )函数基本使用 AVG()函数基本使用 MAX()函数基本使用 MIN()函数基本使用 字符函数 concat()和concat_ws() LEFT()与R ...