工具 | 一条 SQL 实现 PostgreSQL 数据找回

工具 | 一条 SQL 实现 PostgreSQL 数据找回作者:张连壮 PostgreSQL 研发工程师 从事多年 PostgreSQL 数据库内核开发,对 citus 有非常深入的研究。 快速找回丢失数据,是数据库的一项重要功能需求,一般建议使用官方推荐的

工具 | 一条 SQL 实现 PostgreSQL 数据找回

作者:张连壮 PostgreSQL 研发工程师

从事多年 PostgreSQL 数据库内核开发,对 citus 有非常深入的研究。

快速找回丢失数据,是数据库的一项重要功能需求,一般建议使用官方推荐的工具。面向开源数据库,生态中也出现很多好用的开源工具。

PostgreSQL 是非常流行的开源数据库,接下来介绍一款近期在社区开源的 PostgreSQL 数据找回工具 pg_recovery ,并实例演示如何找回误操作而丢失的数据。

| 什么是 pg_recovery?

pg_recovery 是一款 PostgreSQL 数据找回工具。可以恢复 COMMIT / DELETE / UPDATE / ROLLBACK / DROP COLUMN 操作后导致的数据变化,并以表的形式返回。安装方便,操作简单。仓库地址:https://github.com/radondb/pg_recovery

快速安装

根据环境配置 PG_CONFIG。

$ make PG_CONFIG=/home/lzzhang/PG/postgresql/base/bin/pg_config
gcc -Wall -Wmissing-prototypes -Wpointer-arith -Wdeclaration-after-statement -Werror=vla -Wendif-labels -Wmissing-format-attribute -Wformat-security -fno-strict-aliasing -fwrapv -fexcess-precision=standard -Wno-format-truncation -Wno-stringop-truncation -g -g -O0 -fPIC -I. -I./ -I/home/lzzhang/PG/postgresql/base/include/server -I/home/lzzhang/PG/postgresql/base/include/internal  -D_GNU_SOURCE   -c -o pg_recovery.o pg_recovery.c
gcc -Wall -Wmissing-prototypes -Wpointer-arith -Wdeclaration-after-statement -Werror=vla -Wendif-labels -Wmissing-format-attribute -Wformat-security -fno-strict-aliasing -fwrapv -fexcess-precision=standard -Wno-format-truncation -Wno-stringop-truncation -g -g -O0 -fPIC -shared -o pg_recovery.so pg_recovery.o -L/home/lzzhang/PG/postgresql/base/lib    -Wl,--as-needed -Wl,-rpath,"/home/lzzhang/PG/postgresql/base/lib",--enable-new-dtags  

$ make install PG_CONFIG=/home/lzzhang/PG/postgresql/base/bin/pg_config
/usr/bin/mkdir -p "/home/lzzhang/PG/postgresql/base/lib"
/usr/bin/mkdir -p "/home/lzzhang/PG/postgresql/base/share/extension"
/usr/bin/mkdir -p "/home/lzzhang/PG/postgresql/base/share/extension"
/usr/bin/install -c -m 755  pg_recovery.so "/home/lzzhang/PG/postgresql/base/lib/pg_recovery.so"
/usr/bin/install -c -m 644 .//pg_recovery.control "/home/lzzhang/PG/postgresql/base/share/extension/"
/usr/bin/install -c -m 644 .//pg_recovery--1.0.sql  "/home/lzzhang/PG/postgresql/base/share/extension/"

初始化插件成功,返回如下信息。

$ create extension pg_recovery ;
CREATE EXTENSION

| 数据找回演示

1. 准备初始化数据

准备一个表和一些数据。

$ create table lzzhang(id int, dp int);
CREATE TABLE
# insert into lzzhang values(1, 1);
INSERT 0 1
$ insert into lzzhang values(2, 2);
INSERT 0 1

2. 找回 UPDATE 数据

对数据进行变更操作,不加 WHERE 条件。

$ update lzzhang set id=3, dp=3;
UPDATE 2
lzzhang=# select * from pg_recovery("lzzhang") as (id int, dp int);
 id | dp 
----+----
  1 |  1
  2 |  2
(2 rows)

$ select * from lzzhang;
 id | dp 
----+----
  3 |  3
  3 |  3
(2 rows)

3. 找回 DELETE 数据

尝试恢复 DELETE 的数据。

$ delete from lzzhang;
DELETE 2
lzzhang=# select * from lzzhang;
 id | dp 
----+----
(0 rows)

$ select * from pg_recovery("lzzhang") as (id int, dp int);
 id | dp 
----+----
  1 |  1
  2 |  2
  3 |  3
  3 |  3
(4 rows)

4. 找回 ROLLBACK 数据

尝试恢复回滚操作之前的数据。

$ begin ;
BEGIN
$ insert into lzzhang values(4, 4);
INSERT 0 1
$ rollback ;
ROLLBACK
$ select * from lzzhang;
 id | dp 
----+----
(0 rows)

$ select * from pg_recovery("lzzhang") as (id int, dp int);
 id | dp 
----+----
  1 |  1
  2 |  2
  3 |  3
  3 |  3
  4 |  4
(5 rows)

5. 找回 DROP COLUMN 数据

尝试恢复表中被删除的列及数据。

$ alter table lzzhang drop column dp;
ALTER TABLE
$ select attnum from pg_attribute, pg_class where attrelid = pg_class.oid and pg_class.relname="lzzhang" and attname ~ "dropped";
 attnum 
--------
      2
(1 row)

$ select * from lzzhang;
 id 
----
(0 rows)

$ select * from pg_recovery("lzzhang") as (id int, dropped_attnum_2 int);
 id | dropped_attnum_2 
----+------------------
  1 |                1
  2 |                2
  3 |                3
  3 |                3
  4 |                4
(5 rows)

-- dropped_attnum_2: if the drop attnum is 5, set dropped_attnum_2 to dropped_attnum_5

6. 显示找回数据

显示该表历史上所有写入过的数据。

$ insert into lzzhang values(5);
INSERT 0 1
$ select * from lzzhang;
 id 
----
  5
(1 row)

$ select * from pg_recovery("lzzhang", recoveryrow => false) as (id int, recoveryrow bool);
 id | recoveryrow 
----+-------------
  1 | t
  2 | t
  3 | t
  3 | t
  4 | t
  5 | f
(6 rows)

注意事项

  • 支持的 PostgreSQL 版本

目前 pg_revovery工具已支持 PostgreSQL 12/13/14 。

  • 可恢复事务数

PostgreSQL 通过参数 vacuum_defer_cleanup_age 值大小,可限制可恢复的事务数。如果预期需要恢复的数据量较大,可通过配置参数值,提高可恢复的事务数。

pg_recovery 通过读取 PostgreSQL dead 元组来恢复不可见的表数据。如果元组被 vacuum 清除掉,那么 pg_recovery 便不能恢复数据。

  • 锁请求

pg_recovery 使用期间,支持正常的读表的锁请求。此外 pg_recovery未使用期间,不会对数据库造成任何额外的开销或是影响,无需暂停服务。

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。
转载请注明出处: https://daima100.com/5686.html

(0)
上一篇 2023-04-29
下一篇 2023-04-29

相关推荐

  • Python函数参数默认值错误

    Python函数参数默认值错误Python函数的参数默认值是指在定义函数时为某些参数设置的一个默认值,这样在函数调用时如果没有给这些参数传值,就会使用默认值。在Python中,默认参数是通过在参数名后面加上=和默认值来定义的。例如:

    2024-03-04
    80
  • 快速回顾MySQL:简单查询操作「建议收藏」

    快速回顾MySQL:简单查询操作「建议收藏」利用空闲时间花几分钟回顾一下 7.1 检索数据 为了查询出数据库表中的行(数据),使用SELECE语句。 格式: 第一种写法使用 通配符,会把表中行的列全部查询出来,而不必取一一列出全部列。但是不推

    2023-01-23
    148
  • Python引入模块的方法

    Python引入模块的方法Python是一种功能强大的编程语言,具有开放性和易于学习的特点。在Python中,模块是对代码的组织形式,这使得代码可以分解为可维护的组件。通过模块化,程序员可以更好地组织和重用现有的代码,从而保证代码的可维护性、可读性和可扩展性。在本文中,我们将介绍Python引入模块的方法,并探讨一些关键的概念和技术。

    2024-07-23
    39
  • 写一手好SQL,你该从哪里入手?[通俗易懂]

    写一手好SQL,你该从哪里入手?[通俗易懂]有时候我们会遇到:在查询sql的时候,假如有100w条数据,会出现慢sql告警,这个时候你就应该到处sql日志来查找原因了。这里很有可能的主要原因就是没有命中索引和没有分页处理(原因有很多种,主要分…

    2023-02-18
    157
  • win7安装Python教程

    win7安装Python教程Python是一种高级编程语言,其简单易学、易读、易维护的特性使得它成为了学习编程的最佳入门之一。

    2024-04-20
    70
  • Python Read Lines:从文件中读取多行文本

    Python Read Lines:从文件中读取多行文本Python Read Lines是从文件中读取多行文本的基础操作之一,十分常用。在每个Python项目的不同阶段,我们都需要从多个文件中读取文本,将其处理并展示出来。Python Read Lines是这种情况下最实用的方式之一,它允许我们快速有效地访问文件中的多行文本。

    2024-02-21
    94
  • Redis缓存击穿,雪崩,穿透解决方案[亲测有效]

    Redis缓存击穿,雪崩,穿透解决方案[亲测有效]缓存穿透 缓存穿透是指查询一个一定不存在的数据,由于缓存是不命中时被动写的,并且出于容错考虑,如果从存储层查不到数据则不写入缓存,这将导致这个不存在的数据每次请求都要到存储层去查询,失去了缓存的意义。

    2023-02-10
    147
  • update 三种更新用法_修改多条语句sql

    update 三种更新用法_修改多条语句sql1. update用法示例 原表: 2. SQL语句: UPDATE test_table SET name='BBBB' WHERE id=4; 3. 结果:

    2023-02-07
    153

发表回复

您的电子邮箱地址不会被公开。 必填项已用*标注