美文网首页
Flink CDC 源码学习(一)

Flink CDC 源码学习(一)

作者: 无色的叶 | 来源:发表于2023-11-13 11:59 被阅读0次

    一、核心设计

    CDC2.4版本支持先同步全量数据(Snapshot阶段)后自动切换读取增量数据(Binlog阶段)

    1、切片划分

    全量阶段数据读取方式为分布式读取,会先对当前表数据按主键划分成多个Chunk,后续子任务读取Chunk 区间内的数据。根据主键列是否为自增整数类型,对表数据划分为均匀分布的Chunk及非均匀分布的Chunk。

    1.1、均匀分布

    主键列自增且类型为整数类型(int,bigint,decimal)。查询出主键列的最小值,最大值,按 chunkSize 大小将数据均匀划分,因为主键为整数类型,根据当前chunk 起始位置、chunkSize大小,直接计算chunk 的结束位置。

    //  计算主键列数据区间
    select min(`order_id`), max(`order_id`) from demo_orders;
    
    //  将数据划分为 chunkSize 大小的切片
    chunk-0: [min,start + chunkSize)
    chunk-1: [start + chunkSize, start + 2chunkSize)
    .......
    chunk-last: [max,null)
    

    1.2、非均匀分布

    主键列非自增或者类型为非整数类型。主键为非数值类型,每次划分需要对未划分的数据按主键进行升序排列,取出前 chunkSize 的最大值为当前 chunk 的结束位置。注意如果未设置chunkKeyColumn属性, 且主键为联合字段, 则取主键第一个字段列进行划分

    // 未拆分的数据排序后,取 chunkSize 条数据取最大值,作为切片的终止位置。
    chunkend = SELECT MAX(`order_id`) FROM (
            SELECT `order_id`  FROM `demo_orders` 
            WHERE `order_id` >= [前一个切片的起始位置] 
            ORDER BY `order_id` ASC 
            LIMIT   [chunkSize]  
        ) AS T
    

    1.3、全量切片数据读取

    Flink 将表数据划分为多个Chunk,子任务在不加锁的情况下,并行读取 Chunk数据。因为全程无锁在数据分片读取过程中,可能有其他事务对切片范围内的数据进行修改,此时无法保证数据一致性。因此,在全量阶段Flink 使用快照记录读取+Binlog数据修正的方式来保证数据的一致性。

    1.4、快照读取

    通过JDBC执行SQL查询切片范围的数据记录。

    ## 快照记录数据读取SQL 
    SELECT * FROM `test`.`demo_orders` 
    WHERE order_id >= [chunkStart] 
    AND NOT (order_id = [chunkEnd]) 
    AND order_id <= [chunkEnd]
    

    1.5、数据修正

    在快照读取操作前、后执行 SHOW MASTER STATUS 查询binlog文件的当前偏移量,在快照读取完毕后,查询区间内的binlog数据并对读取的快照记录进行修正。

    BinlogEvents 修正 SnapshotEvents 规则:

    • 未读取到binlog数据,即在执行select阶段没有其他事务进行操作,直接下发所有快照记录。
    • 读取到binlog数据,且变更的数据记录不属于当前切片,下发快照记录。
    • 读取到binlog数据,且数据记录的变更属于当前切片。delete 操作从快照内存中移除该数据,insert 操作向快照内存添加新的数据,update操作向快照内存中添加变更记录,最终会输出更新前后的两条记录到下游。

    单个切片数据处理完毕后会向 SplitEnumerator 发送已完成切片数据的起始位置(ChunkStart, ChunkStartEnd)、Binlog的最大偏移量(High watermark),用来为增量读取指定起始偏移量。

    1.6、增量切片数据读取

    全量阶段切片数据读取完成后,SplitEnumerator 会下发一个 BinlogSplit 进行增量数据读取。BinlogSplit读取最重要的属性就是起始偏移量,偏移量如果设置过小下游可能会有重复数据,偏移量如果设置过大下游可能是已超期的脏数据。而 Flink CDC增量读取的起始偏移量为所有已完成的全量切片最小的Binlog偏移量,只有满足条件的数据才被下发到下游。
    数据下发条件:

    捕获的Binlog数据的偏移量 > 数据所属分片的Binlog的最大偏移量。

    参考: https://www.cnblogs.com/importbigdata/articles/15625753.html

    相关文章

      网友评论

          本文标题:Flink CDC 源码学习(一)

          本文链接:https://www.haomeiwen.com/subject/jpxdwdtx.html