PostgreSQL变更事件捕获 (CDC)

一、前驱知识

CDC与ETL

        数据库在本质上是一个状态集合,任何对数据库的变更(增删改)本质上都是对状态的修改。
        在实际生产中,我们经常需要把数据库的状态同步到其他地方去,例如同步到数据仓库进行分析,同步到消息队列供下游消费,同步到缓存以加速查询。总的来说,搬运状态有两大类方法:ETL与CDC。

  • ETL(Extract Transform Load)着眼于状态本身,用定时批量轮询的方式拉取状态本身。
  • CDC(Changing Data Capture)则着眼于变更事件,以流式的方式持续收集状态变化事件(变更)。

       ETL大家都耳熟能详,每天批量跑ETL任务,从生产OLTP数据库 拉取(E) , 转换(T) 格式, 导入(L) 数仓,在此不赘述。相比ETL而言,CDC算是个新鲜玩意,随着流计算的崛起也越来越多地进入人们的视线。

       变更数据捕获(change data capture, CDC)是一种观察写入数据库的所有数据变更,并将其提取并转换为可以复制到其他系统中的形式的过程。 CDC很有意思,特别是当变更能在被写入数据库后立刻用于后续的流处理时。

       例如用户可以捕获数据库中的变更,并不断将相同的变更应用至搜索索引(e.g elasticsearch)。如果变更日志以相同的顺序应用,则可以预期的是,搜索索引中的数据与数据库中的数据是匹配的。同理,这些变更也可以应用于后台刷新缓存(redis),送往消息队列(Kafka),导入数据仓库(EventSourcing,存储不可变的事实事件记录而不是每天取快照),收集统计数据与监控(Prometheus),等等等等。在这种意义下,外部索引,缓存,数仓都成为了PostgreSQL在逻辑上的从库,这些衍生数据系统都成为了变更流的消费者而PostgreSQL成为了整个数据系统的主库。在这种架构下,应用只需要操心怎样把数据写入数据库,剩下的事情交给CDC即可。系统设计可以得到极大地简化:所有的数据组件都能够自动与主库在逻辑上保证(最终)一致。用户不用再为如何保证多个异构数据系统之间数据同步而焦头烂额了。

       实际上PostgreSQL自10.0版本以来提供的逻辑复制(logical replication)功能,实质上就是一个CDC应用:从主库上提取变更事件流:INSERT, UPDATE, DELETE, TRUNCATE,并在另一个PostgreSQL主库实例上重放。如果这些增删改事件能够被解析出来,它们就可以用于任何感兴趣的消费者,而不仅仅局限于另一个PostgreSQL实例。

二、逻辑复制

       想在传统关系型数据库上实施CDC并不容易,关系型数据库本身的预写式日志WAL 实际上就是数据库中变更事件的记录。因此从数据库中捕获变更,基本上可以认为等价于消费数据库产生的WAL日志/复制日志。(当然也有其他的变更捕获方式,例如在表上建立触发器,当变更发生时将变更记录写入另一张变更日志表,客户端不断tail这张日志表,当然也有一定的局限性)。

       大多数数据库的复制日志的问题在于,它们一直被当做数据库的内部实现细节,而不是公开的API。客户端应该通过其数据模型和查询语言来查询数据库,而不是解析复制日志并尝试从中提取数据。许多数据库根本没有记录在案的获取变更日志的方式。因此捕获数据库中所有的变更然后将其复制到其他状态存储(搜索索引,缓存,数据仓库)中是相当困难的。

       此外,仅有 数据库变更日志仍然是不够的。如果你拥有 全量 变更日志,当然可以通过重放日志来重建数据库的完整状态。但是在许多情况下保留全量历史WAL日志并不是可行的选择(例如磁盘空间与重放耗时的限制)。 例如,构建新的全文索引需要整个数据库的完整副本 —— 仅仅应用最新的变更日志是不够的,因为这样会丢失最近没有更新过的项目。因此如果你不能保留完整的历史日志,那么你至少需要包留一个一致的数据库快照,并保留从该快照开始的变更日志。
因此实施CDC,数据库至少需要提供以下功能:
    1.获取数据库的变更日志(WAL),并解码成逻辑上的事件(对表的增删改而不是数据库的内部表示)
    2.获取数据库的"一致性快照",从而订阅者可以从任意一个一致性状态开始订阅而不是数据库创建伊始。
    3.保存消费者偏移量,以便跟踪订阅者的消费进度,及时清理回收不用的变更日志以免撑爆磁盘。

我们会发现,PostgreSQL在实现逻辑复制的同时,已经提供了一切CDC所需要的基础设施:
逻辑解码(Logical Decoding),用于从WAL日志中解析逻辑变更事件
复制协议(Replication Protocol):提供了消费者实时订阅(甚至同步订阅)数据库变更的机制
快照导出(export snapshot):允许导出数据库的一致性快照(pg_export_snapshot)
复制槽(Replication Slot),用于保存消费者偏移量,跟踪订阅者进度。

因此,在PostgreSQL上实施CDC最为直观优雅的方式,就是按照PostgreSQL的复制协议编写一个"逻辑从库" ,从数据库中实时地,流式地接受逻辑解码后的变更事件,完成自己定义的处理逻辑,并及时向数据库汇报自己的消息消费进度。就像使用Kafka一样。在这里CDC客户端可以将自己伪装成一个PostgreSQL的从库,从而不断地实时从PostgreSQL主库中接收逻辑解码后的变更内容。同时CDC客户端还可以通过PostgreSQL提供的复制槽(Replication Slot)机制来保存自己的消费者偏移量,即消费进度,实现类似消息队列一至少次的保证,保证不错过变更数据。(客户端自己记录消费者偏移量跳过重复记录,即可实现"恰好一次 "的保证 )

参考链接: https://developer.aliyun.com/live/1103

  • 0
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
PostgreSQL 是一个开源的关系型数据库管理系统,它提供了ACID事务支持和高度可扩展性。它是许多企业和组织使用的首选数据库之一。而Flink是一个用于大规模数据处理和分析的开源流处理框架,可以实时处理和分析大量的数据流。CDC是Change Data Capture(数据变更捕获)的缩写,是一种用于捕获和传送数据库变更的技术。 PostgreSQL CDC是一种将数据库变更实时捕获并传送到其他系统的技术。它可以用于实时数据分析、数据同步和数据复制等场景。Flink提供了与PostgreSQL CDC集成的功能,通过Flink的CDC connector可以捕获PostgreSQL数据库数据变更,并实时处理这些变更。 使用Flink的PostgreSQL CDC功能,可以将数据变更捕获成流,并进行实时的数据处理和分析。当PostgreSQL中的数据发生变更时,例如插入、更新或删除操作,Flink将会实时获取这些变更,并将其转换成流数据进行处理。这样,我们就可以实时对数据库变更进行监控、实时计算或者实时分析等操作。 通过将PostgreSQL CDC与Flink结合使用,可以实现实时的数据处理和分析,具有低延迟和高吞吐量的特点。这对于一些要求实时更新的应用场景非常有用,例如实时报表生成、实时数据仪表盘、实时监控和实时通知等。 总之,PostgreSQL CDC与Flink的集成使得我们能够实现对PostgreSQL数据库的实时数据捕获和处理,为实时数据分析和应用提供了便利。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值