熟悉pg_probackup。第二部分

图片



我们继续熟悉pg_probackup工具



第一部分中,我们安装了pg_probackup,创建并配置了一个实例,进行了两次备份-DELTA模式下的完整备份和增量备份,学习了如何查看和更改实例配置。我们得到了一个备份列表,编写了一个脚本(bkp_base.sh),该脚本备份集群并将上次备份操作的结果发送到监视系统。今天,我们将处理同样有趣的任务。



问题2



鉴于:我们有两台服务器,第一台具有数据库(主机名srv_db1,用户postgres),第二台将存储备份(主机名srv_bkp,用户backup_user)。但是,除了在同一台服务器上进行备份外,我们还将存储预记录日志的副本,以便能够在最近3天内还原到任意时间点(时间点恢复)。



解决方案:



为了能够还原到选定的时间点(还原点),我们必须在还原点之前进行备份,以及从备份开始到还原点的所有WAL文件。



我们已经有备份,仍然需要在srv_bkp上配置WAL归档。

使用postgres用户连接到srv_db1并执行以下命令:



ssh-keygen -t rsa
ssh-copy-id backup_user@srv_bkp


让我们将〜/ .ssh / autorized_keys文件修改为srv_bkp:



command="pg_probackup-12 agent" ssh-rsa AAAA....


回到srv_db1,您需要启用归档模式(archive_mode)并配置archive_command参数。它包含一个用于备份整个WAL段的命令。



psql -c 'show archive_mode'


如果它熄灭,则更改为开



psql -c 'alter system set archive_mode = on'


为了应用更改,您需要重新启动PostgreSQL,但是现在我们将推迟此操作并再配置一个参数。



如果WAL文件流足够大,则备份服务器可能很快就会用完空间,因此我们可以在archive_command行中插入--compress选项,然后日志文件将被压缩,然后发送到srv_bkp。而且,我们无需担心在恢复过程中将这些文件分别解压缩的事实-pg_probackup可以处理压缩文件。



alter system set archive_command = 'pg_probackup-12 archive-push -B /home/backup_user/backup_db --instance=db1 --wal-file-path=%p --wal-file-name=%f --remote-host=srv_bkp --remote-user=backup_user --compress';


现在您可以重新启动。



我们在第一个任务中所做的工作称为脱机备份。之所以这样称呼,是因为这样的副本包含恢复它所必需的所有WAL文件。在当前任务中,我们正在从脱机副本移至归档副本,此类副本中不包含必需的日志,但这无关紧要,因为我们将需要的所有WAL文件保存到归档中。从备份副本还原时,将从存档中复制WAL文件。



由于在考虑中的情况下,我们正在从脱机备份(以流模式进行备份)切换为已存档(以存档模式),因此可能会出现以下情况:在尚未启用存档模式时我们进行了复制,此后一些WAL段已经出现。删除。这意味着切换到存档模式后的第一次备份无法在PAGE模式下进行,因为 归档文件中过去和当前副本之间的WAL段可能不完整。



让我们使用在第一个任务中创建的脚本来执行此操作:



./bkp_base.sh DELTA


然后,我们将以PAGE模式创建第一个备份



./bkp_base.sh PAGE


让我提醒您,有三种可用的增量模式:PAGE,DELTA和PTRACK。它们在获取有关已更改页面的必要信息的方式上彼此不同:



  • DELTA ,
  • PAGEWAL , ,
  • PTRACK — - Block Change Tracking Oracle — , . ( ..). , .


现在让我们考虑一下,为了能够从中恢复,备份副本需要在备份创建过程中创建的WAL文件。那些。如果我们进行30分钟的增量备份,并且在这30分钟内创建了10 GB的WAL,则仅需要这10 GB,以便我们能够从中持续恢复。所有其他WAL文件仅用于时间点恢复。



该任务表明我们希望能够在过去3天的任何时间恢复。也就是说,必须保存此期间的所有WAL,此外,还必须保存从以前的备份还原所需的所有WAL,但是我们不需要存储所有其他WAL文件!



而且,如果我们可以使用find命令删除过时的WAL,在其中添加mtime和-exec rm {},那么确定需要哪个WAL段来一致地还原特定备份就变得不容易了。最好让开发人员考虑一下,并添加了--wal-depth参数,您可以使用该参数设置在备份中计算出的WAL存储深度。



可以用以下方式示意性地描述:







请注意,现在它位于星期六的中午某处,这意味着我们可以删除恢复三天以上的备份(图表上的棕色)不需要的所有WAL文件。仍然需要的那些WAL以黄色突出显示。这里可能会出现一个逻辑问题-但毕竟已经是星期六的中午了,这意味着不再需要在星期三创建的某些早晨日志,可以将其删除。是的,是这样,您可以至少每分钟配置一次删除多余的WAL,但是在我们的文章中,我们将在创建备份的同时删除日志,因此尽管它们不再属于保留策略,但是在创建下一个备份时将删除它们。 ...



更改db1实例的设置-添加WAL文件的生存期



pg_probackup set-config --instance db1 --wal-depth=3


让我们检查设置是否已应用:



pg_probackup show-config --instance=db1 | grep wal-depth


bkp_base.sh脚本的backup命令中添加--delete-wal标志,并删除--stream开关,因为我们正在从脱机备份切换到存档备份



pg_probackup backup --instance=db1 -j 2 --progress -b $1 --compress --delete-expired --delete-wal


目前,我们已在另一台服务器上配置了存档备份的创建。另外,在此处添加了日志文件,这使我们不仅有机会对特定的备份使用恢复,而且还可以执行时间点恢复-恢复到特定的时间点。



由于现在有了WAL文件的存档,我们可以使用PAGE模式创建增量备份,让我提醒您,在此模式下,相对于先前备份的更改不是由数据文件计算的,而是由自上次备份以来累积的WAL计算的。



PS仅用于教育目的!让我们在srv_db1服务器上的数据库中创建一个表:



psql -c 'create table timing(time_now timestamp with time zone)'


然后将以下行写入crontab:



* * * * * psql -c 'insert into timing(select now())'


每分钟,有关当前时间的信息都会记录在数据库中,当我们恢复到某个时间点时,此信息对我们很有用。



问题3



鉴于:



我们有两台服务器,第一台拥有数据库(主机名srv_db1,用户postgres),第二台存储存档的备份和WAL文件(主机名srv_bkp,用户backup_user)。另一个服务器srv_db2出现在我们的环境中(用户postgres),在该服务器上,我们将必须部署集群的副本并重新配置pg_probackup,以便从副本获取备份。



决定:



互联网上充满了有关如何在PostgreSQL中创建副本的描述,您只需要将“在PostgreSQL中创建副本”驱动到搜索引擎中-选择,我不想!有文档,文章,甚至是视频教程。所有这些方法都不错,但是它们通常没有考虑到我们已经有备份。我们想使用备份创建副本,因此我们消除了原版的读取负担。也就是说,我们的生产服务器不会知道在其附近的某个地方正在创建副本(当然,这是有保留的,这里将需要创建复制插槽并设置访问权限,但是在创建副本时,主服务器上没有额外的负载不会是)。



我们通过srv_bkp和srv_db2服务器之间的密钥来设置访问权限,在srv_db2上安装PostgreSQL和pg_probackup(在第一个任务中,我们完成了除PostgreSQL安装之外的所有操作,但是如果您对安装DBMS有任何疑问,请在此处查看)。



转到srv_db2



ssh-keygen -t rsa
ssh-copy-id backup_user@srv_bkp


转到srv_bkp



ssh-copy-id postgres@srv_db2


让我们打开内部偏执并编辑〜/ .ssh / autorized_keys-插入



command="pg_probackup-12 agent"


在新密钥之前。



使用WAL文件比从备份还原要慢得多,因此让我们创建另一个增量备份-使用backup_user连接到srv_bkp服务器并运行以下命令:



pg_probackup backup --instance=db1 -j 2 --progress -b PAGE --compress


我们为什么不使用我们创建的脚本?事实是,我们之前在脚本中添加了--delete-wal选项,也就是说,在创建此备份之后,我们将无法还原到三天前的某个时间点。但是,如果我们保留该备份,则通过运行脚本进行的下一次备份仍将仅在最后两天离开WAL,也就是说,从该备份中恢复后,删除它是有意义的。



我们进行恢复:



time pg_probackup restore --instance=db1 -D /var/lib/pgsql/12/data -j 2 --restore-as-replica --progress --remote-proto=ssh --remote-host=srv_db2 --archive-host=srv_bkp --archive-user=backup_user --log-level-console=log --log-level-file=verbose --log-filename=restore_rep.log


/ var / lib / pgsql / 12 / data目录必须为空,此外,在srv_db1服务器上,必须对pg_hba.conf进行更改-允许使用复制协议从srv_db2服务器进行访问。



host    replication     all             srv_db2                 md5


我们重新阅读配置:



psql -c 'select pg_reload_conf()'


检查拼写错误:



psql -c 'select * from pg_hba_file_rules'


在srv_db2上创建一个〜/ .pgpass文件,在其中我们在srv_db1中指定连接权限,但这一次使用复制基础并启动PostgreSQL。



srv_db1:5432:replication:backup:Strong_PWD


然后将其权限更改为600:



chmod 600 ~/.pgpass


我们在srv_db2上启动集群。



让我们检查一切是否正常。为此,我们将使用以下可能性。



我们查看其中的副本日志文件,在结尾处附近,应显示以下行:



Database system is ready to accept read only connections


psql -c 'select pg_is_in_recovery()' 


应该返回t



现在让我们在向导上创建一个板t1:



srv_db1: psql -c 'create table t1()'


让我们检查它是否出现在副本中。



srv_db2: psql -c '\d'


板就位,然后复制正常。我们卸下母版上的印版。



srv_db1: psql -c 'drop table t1'


当然,在真实数据库上,您现在应该在主数据库上创建一个复制插槽并配置副本,以便它通过该插槽进入主数据库,但是本文的主题不是副本,而是备份,因此让我们继续。



因此,副本对我们有用,如果有必要,我们可以切换到副本,但让我们问一个问题-我们可以做得更好吗?

当然可以。当我们可以从主机上删除读取负载并将其转移到副本时,为什么需要从主机上进行备份?



警告!必须监控REPLICA的延迟,否则可能会导致您不知道REPLICA的延迟,并且将继续从REPLICA的延迟进行备份。



让我们开始吧!



我们对srv_db1和srv_db2服务器上的集群设置进行更改:



alter system set archive_timeout=180;
select pg_reload_conf();


转到srv_bkp并更改remote-host参数的值:



pg_probackup set-config --instance db1 --remote-host=srv_db2


我们在srv_bkp服务器上对.pgpass进行更改-将连接字符串添加到srv_db2服务器:



srv_db2:5432:replication:backup:Strong_PWD
srv_db2:5432:backupdb:backup:Strong_PWD


让我们尝试进行另一个备份。



srv_bkp: ./bkp_base.sh PAGE


我们看到备份已经生效。



问题已经解决了!



下一部分将专门介绍如何从备份还原:我们将考虑各种恢复选项,了解如何还原到特定的备份,到某个时间点,熟悉部分还原和增量还原。



All Articles