PostgreSQL数据库复制
这篇博客的行文可能有点“官方”,因为是之前为了发期刊而写的初稿。 postgersql是一款功能强大的开源数据库系统。它基于并扩展了SQL语言,使之支持更复杂的数据类型。它提供了丰富的接口,可以很容易地扩展它的功能,比如最知名的地理空间数据库扩展PostGIS。PostgreSQL以其稳定性、可扩展性以及软件背后开源社区的奉献精神而赢得了良好的声誉,并得到了广泛的应用。 数据库复制是指在多个数据库节点之间完整一致地共享数据的过程。不论其具体使用场景如何,数据库复制的目的都是为了实现数据库的高可用性与负载均衡。高可用性是指当主节点失效的时候,备用节点能快速接手工作;负载均衡是指将工作分流给多个节点,以平衡每个节点的压力。 我们希望多个数据库节点可以无缝地协同工作,但是实际上,只有用做只读服务器的节点能够相对容易的结合在一起。大部分情况下,数据库收到的请求都是读写混合的,对于任意节点的一次写入动作必须实时的传播给其他节点,这样才能保证后续对任意节点的读取请求能够返回一致的结果。如何保证多个节点的数据一致性是数据库复制技术的难题,也是数据库协同工作的核心。PostgreSQL支持多种实现数据库复制的技术方案,每种方案都各有其优缺点,都是为了满足特定环境下的特定需求。 有的方案只允许在一个节点上进行写操作,这个可写的节点称为主节点(主服务器)。其他从主节点复制数据的则称为从节点(从服务器)。另外,从节点又根据其是否可读分为温备与热备。温备是指从节点只有当被提升为主节点的时候才允许用户连接进行读写操作,热备是指从节点任何时候都可以处理读取请求。除了主从复制方案,有时候我们会需要双向复制方案,来实现任意节点都可读写的需求。 有的方案是同步复制的,即一个数据修改事务只有到所有节点均提交了该事务后才能被认为是提交成功的。相反有些方案是异步的,即允许事务在某个节点上的提交与它被传播到其他节点之间存在延迟。异步复制会导致在某些时刻两个节点的数据不一致,但是它对于网络延迟的要求比同步复制宽容的多。 有的方案只能对整个数据库节点进行复制,有的则允许细分到每个库,甚至每张表的复制。 1 流复制 1.1 预写式日志(WAL) 预写式日志(WAL, Write Ahead Log)是PostgreSQL内置复制技术的基石,其作用与Oracle数据库的重做日志类似,都是用于保证数据的一致性以及事务的完整性。WAL的核心概念是数据文件的修改必须在这些动作被日志记录之后才被写入[1]。只要有了数据库的一个早期基础备份,以及后续的WAL文件,那么不论是在系统崩溃需要恢复的时候,还是在另一台机器重建数据库的时候,都可以很容易的通过重放WAL中的日志项来还原数据库,达到WAL记录中任意时间点的状态。我们将这种恢复数据库的方案叫做时间点恢复(PITR, Point In Time Recovery),这也是PostgreSQL流复制与逻辑复制的基本原理。 WAL文件被存储在数据库目录的pg_wal子目录下,默认大小为16MB。可以通过postgresql.conf配置文件中的wal_level配置项来决定有多少日志信息输出到WAL中。wal_level分为三个等级,minimal表示只输出最基本的日志信息,以供系统崩溃或异常停机时候恢复数据所用;replica表示输出足够的日志信息以支持WAL归档和复制,这是WAL的默认等级;logical表示增加支持逻辑解码所需的信息,这是PostgreSQL内置的逻辑复制需要的等级。 […]