Flink 应用的一致性保障
应用一致性保障
在Flink中,会自动做检查点,用于故障时恢复一个应用。在恢复时,application的state信息可以根据最近完成的检查点进行重建,并继续运行。不过,仅将一个application的state进行重置并不足以满足exactly-once的保证。
为了给一个应用提供exactly-once保证,在应用根据检查点重置state时,它的每个source connector都应该有能力将它的read position重置到做检查点时的read position。在做一个检查点时,source operator将它的read position也持久化,并在恢复时根据此位置进行重置。对于这类可以重置read position的source connector,比较有代表性的有:
- 基于文件的源:可以存储读文件字节流时的偏移量
- Kakfa:可以存储读入topic partition的偏移量
如果一个application从一个无法重置read position的source connector读数据,则在故障发生并恢复时,只能提供at-most-once 的保证。
Flink的检查点与恢复机制、结合可重置reading position的source connector,可以确保一个应用不会丢失任何数据。但是,此应用仍可能输出同一数据两次。因为若是应用故障发生在两次检查点之间,则必定会导致已经成功输出的数据再次输出一次。所以仅通过Flink与source connector的行为,并不足以提供端到端的exactly-once保证,即使application的state具有exactly-once的保证。
一个application若是需要提供端到端exactly-once 的保证,则需要特殊的sink connectors。对于sink connectors来说,有两种技术可以应用于不同的场景,用于达到exactly-once的保证,分别为:idempotent writes、以transactional writes。
Idempotent Writes
一个idempotent 操作可被执行多次,但是仅会产生一个变化。例如向一个hashmap中插入同样的key-value pair,这即为一个idempotent操作。因为仅有第一次操作会在hashmap中增加此条目,而之后的插入不会改变hashmap中的内容。一个非 idempotent 操作的例子如追加操作,即使是同样的数据,每次追加都会增加一条数据。在流应用中,idempotent write是一个很有特点的操作,它们可以多次执行,但并不改变最终的结果。所以在Flink根据检查点机制进行恢复时,可以在一定程度上缓解replay对结果造成的影响(或是没有影响)。
需要注意的是,若是一个应用依赖于idempotent sinks,以达到exactly-once 的结果,则必须保证的是:在replay时覆盖之前写的结果。一般来说,只要流应用在replay时正常执行并输出,在新的输出覆盖掉之前写的结果后,即可以正常到达一致状态。
Transactional Writes
第二种实现端到端exactly-once 一致性的方法是基于transactional writes。这个方法基于的想法是:仅在最近一个检查点成功完成后,才将所有结果写入到一个外部的sink系统。这个行为可以实现端到端exactly-once的原因是因为:在故障发生时,应用会被重置到最近的检查点,并且在此检查点之后,没有任何结果被写入到外部sink系统。但是此方法会增加延时,因为结果仅能在一个检查点完成后才能看到。
Flink提供了两种方式分别实现transactional sink connectors – 一个通用的 write-ahead-log(WAL
)以及一个two-phase-commit(2PC)sink。WAL
sink将所有result
records写入应用的state,并在它收到了一个“检查点完成”的通知后,将结果输出到sink
系统。因为WAL
sink会将result
records缓存到state
backend,所以它可以用于任何sink
系统中。然而,使用此方法实现的exactly-once仍会有些代价:增加了应用的state大小,并且sink
系统需要处理突增写入的模式。
与WAL不同的是,2PC sink需要sink
system提供事务支持,或者提供模拟事务的支持。对于每个检查点,sink首先启动一个事务,将所有接收到的记录添加到事务中,并将它们写入sink系统,但是不提交(commit)。当它收到一个“检查点完成”的通知后,它提交事务,并将结果落盘。
2PC协议集成在Flink的检查点机制中。Checkpoint barriers便是启动一个新事务的通知,所有operators中对于它“自身检查点完成”的通知,即是它们的commit
投票。JobManager的对于“整个检查点完成”的消息,即为提交事务的指示。
相对于WAL sinks,2PC sinks是基于sink 系统以及sink的实现方式,达到exactly-once的输出保障。而 相对于WAL sink的突增写入模式,2PC sink为持续向sink
系统写入记录。
下表展示的是对于不同类型的source与sink
connectors,在最优的情况下是否可以达到端到端exactly-once保障的对比(根据sink的实现不同,真正的一致性可能会更差):

References:
Vasiliki Kalavri, Fabian Hueske. Stream Processing With Apache Flink. 2019
Flink 应用的一致性保障的更多相关文章
- zooKeeper_《ZooKeeper官方指南》一致性保障
转 http://ifeve.com/zookeeper-consistency-guarantees/ 本文翻译自<ZooKeeper官方指南>,译者:追云,校对:追云 一致性保障 Zo ...
- flink系列-10、flink保证数据的一致性
本文摘自书籍<Flink基础教程> 一.一致性的三种级别 当在分布式系统中引入状态时,自然也引入了一致性问题.一致性实际上是“正确性级别”的另一种说法,即在成功处理故障并恢复之后得到的结果 ...
- 从flink-example分析flink组件(1)WordCount batch实战及源码分析
上一章<windows下flink示例程序的执行> 简单介绍了一下flink在windows下如何通过flink-webui运行已经打包完成的示例程序(jar),那么我们为什么要使用fli ...
- 超越Storm,SparkStreaming——Flink如何实现有状态的计算
流式计算分为无状态和有状态两种情况.无状态计算观察每个独立的事件,Storm就是无状态的计算框架,每一条消息来了以后和前后都没有关系,一条是一条.比如我们接收电力系统传感器的数据,当电压超过240v就 ...
- Flink State 有可能代替数据库吗?
有状态的计算作为容错以及数据一致性的保证,是当今实时计算必不可少的特性之一,流行的实时计算引擎包括 Google Dataflow.Flink.Spark (Structure) Streaming. ...
- Flink读写Kafka
Flink 读写Kafka 在Flink中,我们分别用Source Connectors代表连接数据源的连接器,用Sink Connector代表连接数据输出的连接器.下面我们介绍一下Flink中用于 ...
- 实时计算框架:Flink集群搭建与运行机制
一.Flink概述 1.基础简介 Flink是一个框架和分布式处理引擎,用于对无界和有界数据流进行有状态计算.Flink被设计在所有常见的集群环境中运行,以内存执行速度和任意规模来执行计算.主要特性包 ...
- 《基于Apache Flink的流处理》读书笔记
前段时间详细地阅读了 <Apache Flink的流处理> 这本书,作者是 Fabian Hueske&Vasiliki Kalavri,国内崔星灿翻译的,这本书非常详细.全面得介 ...
- 分布式系统的一致性算法------《Designing Data-Intensive Applications》读书笔记13
一致性算法是分布式系统中最重要的问题之一.表面上看,这似乎很简单,只是让几个节点在某些方面达成一致.在本篇之中,会带大家完整的梳理分布式系统之中的共识算法,来更加深刻的理解分布式系统的设计. 1.原子 ...
随机推荐
- 浏览器console控制台不显示编译错误/警告
浏览器正常显示报错应该是这样的 ,但是我一不小心右键给Hide message from...了,红色报错字体就没了,解决方法如下: 直接将红色框内的内容叉掉,恢复成filter就OK了
- 【巨杉数据库SequoiaDB】社区分享 | SequoiaDB + JanusGraph 实践
本文来自社区用户投稿,感谢小伙伴的技术分享 项目背景 大家好!在春节这段时间里,由于一直在家,所以花时间捣鼓了一下代码,自己做了 SequoiaDB 和 JanusGraph 的兼容扩展工作. 自己觉 ...
- MySQL的数据库备份
MySQL的数据库备份 备份的原因: 1.保证重要数据不丢失 2.数据转移 MySQL数据库备份方式: 1.方法1:在Sqlyog这种可视化工具中手动导出 2.方法2:直接拷贝物理文件(就是data文 ...
- 在W10系统中配置Java环境变量后,cmd命令提示符找不到java
java环境变量配置在W10系统上和以前有所区别,可能是W10版本导致也可能是W10一开始就出问题. 问题的表现就是你在环境变量里已经配置完JAVA_HOME,CLASSPATH,path之后在控制台 ...
- 305. 岛屿数量 II
题目: 假设你设计一个游戏,用一个 m 行 n 列的 2D 网格来存储你的游戏地图. 起始的时候,每个格子的地形都被默认标记为「水」.我们可以通过使用 addLand 进行操作,将位置 (row, c ...
- Python instagram 爬虫项目
直接介绍一下具体的步骤以及注意点: instagram 爬虫注意点 instagram 的首页数据是 服务端渲染的,所以首页出现的 11 或 12 条数据是以 html 中的一个 json 结构存在的 ...
- 归并排序 ALDS1_5_B:Merge Sort
Merge Sort Write a program of a Merge Sort algorithm implemented by the following pseudocode. You sh ...
- Vuejs+elementUI项目,在进行打包时,要注意的问题
注意:打包之前,需要注意修改一些地方 (1)若是前后端分离开发的,前端开发过程中可能会在api.js中设置访问路径为服务器所在电脑的ip:端口,打包前,最好将它改回localhost:8080 (2) ...
- 占位 SC
占位 SC include: SC404 SC405
- Github中进行fork后,原仓库更新了如何与原仓库同步
我们经常在Github中Fork别人优秀的项目(在自己的GitHub下面生成一个repository),如果原仓库作者或组织更新仓库,此时你Fork的项目并不会更新,如果我们想要更新操作,该如何操作? ...