目录

Flink反压问题

Flink反压问题

背景

        在使用flink的过程中,多次遇到过反压(backpressure)的问题,这通常是因为数据处理的速率超过了数据源或下游系统的处理能力导致。

反压的底层剖析

网络流控

        一个重要的概念是网络流控,如上图,不同的Consumer和Producer的消费和生产速率不一样,那么一定时候后,receive buffer和send buffer就肯定会满,导致生产端瘫痪。

为了能提前感知这一问题,引入了反压机制,增加了一个feedback:
        在设计的过程中,会包含正反馈和负反馈,在反压的场景下,就是负反馈,让生产端降低发送速率,甚至停止发送。

在1.5以前,Flink基于TCP实现流控,如图:
https://i-blog.csdnimg.cn/direct/d1212b9729804dde9e7f565eecd8e802.png

ACK=下次从哪个index继续发送
window=最多发送多少个字节


ack=8
window=1

如上表示从第8个字节继续发送,但只能发送1个,从而控制发送端的发送速度

拓展:如果返回window=0,代表接收端buffer已满,发送端会停止发送。为了知道什么时候可以继续发送,发送端会发送一个探测信号zeroWindowProbe来检测接收端的buffer情况。

Flink反压如何传播

https://i-blog.csdnimg.cn/direct/4bf748b8ab3e44058f82435a5b862381.png

简单来说,基于对接收缓冲区的剩余大小感知,如果下游的缓存区满了,信号会从下游不断传递给上游,直到所有算子的所有缓存区均打满。

至于是跨TaskManager还是TaskManager内部,反压的机制是同理的,主要关注不同边界的缓冲区情况。

https://i-blog.csdnimg.cn/direct/cecc4bf70a1e456eb7a32a91cc8cb242.png

跨taskManager的反压示意

https://i-blog.csdnimg.cn/direct/f36bdc87e3124be2863a0dcb51f907ef.png
taskManager内反压示意

基于TCP的反压机制的弊端

        虽然通过TCP可以实现反压机制,但是因为过于通用,还是产生了一些牺牲,因为一个taskManager内可能会有多个Task进行,而多个Task会复用一个socket进行传送(多路复用),如果某个task把tcp打满,会导致Task间相互影响
https://i-blog.csdnimg.cn/direct/4fa870e0876d4ed6bf26e1d0870e79e1.png

Flink1.5之后基于Credit-based的反压机制

        核心是通过Flink应用层来实现TCP流控的机制,避免影响底层tcp网络

https://i-blog.csdnimg.cn/direct/b05c441427604288a4aa6381efd20995.png

反压场景解决

        了解的反压的原理后,在面对Flink反压时,我们核心要分析出哪个环节慢了,然后通过调整并行度,资源分配、性能优化等手段进行解决。

https://i-blog.csdnimg.cn/direct/6ee5dfe9adc04f6e9ad6120a28c4274f.png

具体case

后续补充