将Apache Flink流应用程序与这样的管道一起考虑:
Kafka-Source -> flatMap 1 -> flatMap 2 -> flatMap 3 -> Kafka-Sink
其中每个flatMap
函数都是一个无状态运算符(例如.flatMap
的常规Datastream
函数)。
如果传入消息将在flatMap 3
上待处理,检查点/保存点如何工作?从flatMap 1
开始重新启动后,消息将被重新处理还是跳到flatMap 3
?
我有点困惑,因为documentation似乎将应用程序状态称为我可以在有状态运算符中使用的状态,但是我的应用程序中没有有状态运算符。 是全部保存还是恢复了“处理进度” ,还是在失败/重启后重新处理整个管道?
关于我先前的问题,失败(->从检查点恢复flink)和使用保存点手动重启之间有区别吗?
我试图通过将EXACTLY_ONCE
放在Thread.sleep()
中来找出自己(使用flatMap 3
和rockdb-backend启用检查点),然后使用保存点取消作业。但是,这导致flink
命令行工具一直挂起,直到sleep
结束,甚至flatMap 3
被执行,甚至在发送之前发送到接收器 该作业被取消。因此,似乎无法手动强制这种情况来分析flink的行为。
如果如上所述我的检查点/保存点未保存/覆盖“处理进度”,我如何确保到达管道的每条消息都永远不会重新分配给定的运算符(平面图1/2/3) -在重启/失败情况下处理?
答案 0 :(得分:0)
采用检查点时,每个任务(操作员的并行实例)都会检查其状态。在您的示例中,三个平面图运算符是无状态的,因此没有要检查的状态。 Kafka源是有状态的,并检查所有分区的读取偏移量。
在失败的情况下,将恢复作业,并且所有任务都将加载其状态,这意味着在源操作员的情况下,将重置读取偏移量。因此,应用程序将重新处理自上一个检查点以来的所有事件。
为了一次实现端到端的精确性,您需要一个特殊的接收器连接器,该连接器提供事务支持(例如,针对Kafka)或支持幂等写入。