Flink Event Time 和WaterMark

Flink Event Time 和WaterMark

  • ProcessingTime
  • EventTime
  • WaterMark

ProcessingTime

下面有一个窗口大小为 10s,步长为 5s的滑动窗口 进行数据统计。假设数据源在第13秒(2次)、第16秒分别生成了3条A类型的消息(小时和分钟先不管)。如下:
Flink Event Time 和WaterMark_第1张图片
这些消息将按如下方式落在窗口中。在第13秒生成的前两条消息将同时落在窗口1[5s-15s]和窗口2[10s-20s]中,在第16秒生成的第三条消息将落在窗口2[10s-20s]和窗口3[15s-25s]中。每个窗口发出的最终计数分别为(a,2)、(a,3)和(a,1)。
Flink Event Time 和WaterMark_第2张图片
如果其中一条消息(在第13s生成)延迟6s(19s)到达,那么按上图结算的话,那么这个数据就会落在window2(10-20s)和window315-25的窗口里面,如下:
Flink Event Time 和WaterMark_第3张图片
结果导致window3 和window1的统计结果不对,下面我们看下以EventTime解决这个问题

EventTime

对于使用 EventTime 处理,需要从消息中(事件)提取事件的时间信息,实现 TimestampAssigner extractTimestamp方法。如下:

 env.setStreamTimeCharacteristic(TimeCharacteristic.EventTime);
 public long extractTimestamp(Tuple3<String, Long, Integer> element, long previousElementTimestamp) {
     
    return element.f1;
 }

我们使用了event time 进行处理后,产生的结果如下:

Flink Event Time 和WaterMark_第4张图片
我们发现 window 2 和 window3 的统计结果对的,因为采用了事件的时间,这个事件所携带的事件是13s的因此不会被统计到window3(15s-20s)这个窗口中,但是window 1 没有统计因为窗口已经结算完成了(15s)。

ps:其实window2 也不能说统计对的,因为13s延迟到19s只是恰好在这个窗口里面,假如是延迟8s呢?是不是window2窗口就没有这条数据了。

下面我们使用 watermark 解决这个问题。

WaterMark

WaterMark 对flink 而言是灰常重要的,他的本质就是一个时间戳,当算子收到这个时间戳后,就不会在处理这个时间戳以下的数据了,就是何时不再等待更早的数据了。
我们可以根据事件的event-time,计算出Watermark。在上一个demo 中,没有设置延迟的时间,我们现在将WaterMark设置为:当前时间-5 秒,相当于延迟5秒结算,所以第一个窗口[5s-15s]将仅在第20秒进行结算。同样,窗口[10s-20s]将在第25秒进行结算,以此类推。

private long  currentMaxTimestamp = 0l;
private final long maxOutOfOrderness = 5000l;
@Nullable
@Override
public Watermark getCurrentWatermark() {
     
    return new Watermark(currentMaxTimestamp - maxOutOfOrderness);
}
@Override
public long extractTimestamp(Tuple3<String, Long, Integer> element, long previousElementTimestamp) {
     
    long timestamp= element.f1;
    currentMaxTimestamp = Math.max(timestamp, currentMaxTimestamp);
    return timestamp;
}

统计结果如下:
Flink Event Time 和WaterMark_第5张图片
对于最大延迟时间设置需要根不同的业务和场景设置,设置太小会丢弃延迟的数据。太大会导致窗口一直处于等待状态。
最后留一个关系图供参考:
Flink Event Time 和WaterMark_第6张图片
Thanks for reading 。
参考
[1]: https://ci.apache.org/projects/flink/flink-docs-release-1.8/dev/event_time.html
[2]: https://www.ververica.com/blog/how-apache-flink-manages-kafka-consumer-offsets
[3]: https://blog.csdn.net/xorxos/article/details/80715113

你可能感兴趣的:(flink,flink,watermark,水位线)