4个角度轻松理解 Flink中的Watermark

目录

有缓存就必然有延迟

必须勇敢地输出排序流的第一个结果

watermark 定义了何时不再等待更早的数据

设想不同的策略来生成 watermark


当我们第一次接触 Flink 时往往会对其中的 watermark 感到困惑。但实际上 watermark 并不复杂。在本文中我们将通过一个简单的例子来说明为什么需要水印以及它们如何工作。

在下文中的例子中,我们有一个带有时间戳的事件流,但是由于某种原因流中的事件并不是按顺序到达的。图中的数字代表事件发生的时间戳(Event-time)。第一个事件在时间4达到,它后面跟着的是发生在更早时间(时间 2)的事件,以此类推:

注意这是一个按照事件时间(Event-time)处理的例子,上面所述的时间戳所表示的是事件真实发生时间,而非事件处理的时间(Processing-Time) 。事件时间(Event-Time)处理的强大之处在于,无论是在处理当前的数据还是重新处理历史(数据重放)的数据,基于事件时间创建的流计算应用都可以保证最终执行结果是一致的。

假设我们现在正在尝试创建一个流计算排序算子。即将一个乱序到达的事件流按照事件时间进行顺序输出。数据流中的第一个元素的事件时间是 4,但是我们不能直接将它作为排序后数据流的第一个元素进行输出。因为数据是乱序到达的,也许有一个更早发生的数据还没有到达。实际上,我们在上面的例子中可以提前预知到这个流中元素2 的事件事件比4更早,我们的排序算子至少要等到 2 这条数据的到达后再做输出。

有缓存就必然有延迟

数据流中的第一个元素的事件时间是 4,但是我们不能直接将它作为排序后数据流的第一个元素进行输出。因为数据是乱序到达的,也许有一个更早发生的数据还没有到达。实际上,我们在上面的例子中可以提前预知到这个流中元素2 的事件事件比4更早,我们的排序算子至少要等到 2 这条数据的到达后再做输出。

扫描二维码关注公众号,回复: 12458570 查看本文章

必须勇敢地输出排序流的第一个结果

如果我们假设事件2已经达到,而且我们相信2之前还有更早的事件需要等待,在上面例子中的数据流中, 实际上已经没有比2更早的事件了,我们可能会永远等待下去。总之,我们的应用程序不能保证一定有更早的数据还未到达,所以不能无条件的等下去。

watermark 定义了何时不再等待更早的数据

我们需要某种策略用于定义了对于任何带事件事件的数据流,何时停止等待更早数据的到来。

Flink 中的事件时间处理依赖于一种特殊的带时间戳的元素,称为 watermark,它们会由数据源或是 watermark 生成器插入数据流中。具有时间戳 t 的 watermark 可以被理解为断言了所有时间戳小于或等于 t 的事件都(在某种合理的概率上)已经到达了。

何时我们的排序算子应该停止等待,然后将事件 2 作为首个元素输出?答案是当收到时间戳为 2(或更大)的 watermark 时。

设想不同的策略来生成 watermark

我们知道每个事件都可能会延迟一段时间才到达且这些延迟差异会比较大,有些事件会比其他事件延迟更多。一种简单的方法是假设这些延迟不会超过某个最大值。Flink 把这种策略称作 "有界无序生成策略"(bounded-out-of-orderness)。当然也有很多更复杂的方式去生成 watermark,但是对于大多数常规应用来说,固定延迟方式已经足够了。

往期精选▼

Flink中Checkpoint和Savepoint 的 3 个不同点

Flink实现固定时长或消息条数的触发器 

使用 Broadcast State 的 4 个注意事项

3种Flink State Backend | 你该用哪个?

100%会被问到的两道Flink面试题,你会了么?

识别二维码, 关注我们

猜你喜欢

转载自blog.csdn.net/yscoder/article/details/109697081