Flink的WaterMark詳解

  • WaterMark是什麼?
    在瞭解Flink的WaterMark之前先要了解Flink的時間語義。在Flink裏面有三種時間語義:
    ①Even Time:事件創建的時間,時間在數據裏面。
    ②Ingestion Time:數據進入Flink的時間。
    ③Processing Time:處理數據的本地系統時間。
    由於網絡或者分佈式系統的原因,在進入Flink的數據裏面有的數據是亂序的,如果亂序了,要有一種機制來防止亂序數據影響到數據的最後處理結果,那麼WaterMark就是避免亂序數據帶來的計算不正確的。
    WaterMark是一條特殊的數據,它有一個值,比如設定了延遲是一分鐘,先在WaterMark已經漲到了10:00了,說明10:00以前的數據都已經到齊了,9:59分的數據就可以發車了。WaterMark必須是單調遞增的,它與數據的時間戳有關。
    下面通過圖示來介紹WAaterMark的傳遞:
    在這裏插入圖片描述
    如圖所示,在Flink的任務中有四個並行的子任務,它們初始的WaterMark分別是2,4,3,6,然後第一個子任務的WaterMark爲4的數據來着,到達之後就更新自己的WaterMak變成4,那麼就說明這個子任務的4之前的數據都到了,其他子任務也是一樣。

  • WaterMark的引入和設定
    引入watermark只需要在數據流裏添加一個方法即可:

.assignAscendingTimestamps(_.timestamp * 1000)//設定每一條數據的timestamp爲水位線

參數是指定數據裏面的某一列作爲watermark,也可以直接寫一個數,不過一般不這麼幹,因爲watermark是一直漲的,如果把參數寫死了就說明生成的watermark是一樣的,默認是200ms調用一次這個方法。除了上述方法還可以在參數裏面傳一個函數進去。如果是自定義函數的話就必須實現AssignerWithPeriodicWatermarks或者AssignerWithPunctuatedWatermarks,第一個是週期性生成watermark,後者則是斷點式生成watermark。他們都必須實現的方法如下:
在這裏插入圖片描述
他們各自的兩個方法功能其實是一樣的,第一個就是生成watermark的方法,第二個就是提取時間戳;區別在於生成watermark的方法不一樣,第一個是默認每個200ms調用一次生成watermark的方法,而第二個則是要自己定義什麼時候生成,具體怎麼實現就要看自己怎麼用。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章