抱歉,我打断了您的recovery.conf

我让你康复 在PostgreSQL中,自从很早以前就已经在2005年发布了8.0版本 ,所以使用了一个特殊的配置文件recovery.conf来还原到特定的时间点。 随后,该文件开始用于待机模式和流复制。

但是,自PostgreSQL 12的下一个发行版以来,recovery.conf不再起作用:我破坏了它。
但是为什么呢?

Recovery.conf具有一个特殊性:它仅在DBMS开始时才被读取。 而且,如果仍然可以协调每年需要少于一次的时间点恢复,那么重新启动整个数据库以更改上游复制服务器的地址的需求就会有些沮丧。 我看到了不同的变态方法来规避此限制,例如使用L3路由,级联复制方案(以便分别复制所有副本,但至少只复制一部分),甚至(即使在生产中我没有看到它)。

在下一次计划的副本重新启动后,由于需要更改复制参数,我决定选择它,但是教PostgreSQL重新读取SIGHUP中的primary_conninfo会花费什么呢? 一切都变糟了。 原则上,您只需要在启动过程中更改一个变量,然后从那里请求重新启动WalReceiver-就这样,复制将正确地继续使用新地址。 仍然需要正确地实现它。 几周后,我完成了该补丁,并重新读取了SIGHUP信号上的recovery.conf,而该补丁并未破坏现有的数据库行为。

然后,鼓起勇气, 将他发送到PostgreSQL开发人员邮件列表。 迈克尔·帕奎尔很快回答了一下:
在使其中一些可重载之前,让我们先将它们切换为GUC,而不要像补丁一样重新发明SIGHUP参数处理。
糟糕,事实证明我向搜索引擎提出了错误的问题。 问题不是关于重新读取recovery.conf,而是关于将参数从单独的recovery.conf转换为用于所有其他DBMS参数的GUC基础结构(大统一配置)的问题。 也就是说,绝对不是,我们不需要这样的补丁,我们也不需要。 首先让我们将所有这些设置从recovery.conf转移到我们的标准设置基础结构中。

对于这个令人沮丧的消息,我发火并想到:“但是让我们转移!”。 我阅读了有关正确搜索查询的存档讨论,打开了有关转移设置的最后一个讨论 (该链接由Michael Paquier在他的回答中提供,我对此表示感谢,并感谢他的快速回答)。 当时,在2018年5月,该补丁被放弃了一年多。 因此,我们从这里开始。 还是说“继续”更正确? 根据娱乐计划:

  1. 阅读并列出对补丁程序最新发布版本的更改
  2. 解析补丁中的更改并将必要的内容转移到代码库的当前版本
  3. 修复文档中对recovery.conf及其参数的所有引用
  4. 维修测试
  5. 发送新补丁到邮件列表
  6. 得到任何反馈
  7. 根据意愿改正某些内容并返回第5段
  8. 拒绝再次接受补丁(一年半)

听起来像是一项行动计划? 好吧,我们继续吧!

简短地说,我指出了多长时间,并于2018年6月21日在新的讨论线程中发布了补丁的新版本。 然后3个月,巴斯克维尔斯(Baskervilles)鱼类的寒冷使人无法忍受。 9月底,拥有承诺权的Core开发人员之一Peter Eisentraut突然对补丁产生了兴趣。 经过数次更正之后,尽管我安静地走了几天,去散步看看布达佩斯,看看风景,但彼得·艾森特劳特(Peter Eisentraut)发出了令人沮丧的信:
我浏览了补丁,做了很多小改进。 我还更广泛地更新了文档。 随附的补丁对我来说是可提交的。
也就是说,Peter Eisentraut自行决定更正了一些小问题,更新了文档,刻录了整个recovery-config.sgml部分,并认为以这种形式可以接受该补丁。 哦,我认为只有在postgresql 13上才会发生,即使幸运的是该补丁通常会达到提交准备就绪的状态。

几天后,也就是2018年11月25日,Peter Eisentraut真正接受了此补丁
现在在postgresql.conf(或其他GUC来源)中设置了recovery.conf设置。 当前,所有受影响的设置均为PGC_POSTMASTER; 将来可以根据情况进行细化。
现在,恢复是通过文件recovery.signal启动的。 待机模式由文件standby.signal启动。 待机模式设置消失了。 如果找到了recovery.conf文件,则会发出错误。
作为移动的一部分,trigger_file设置已重命名为promove_trigger_file。
文档章节“恢复配置”已集成到“服务器配置”中。
pg_basebackup -R现在将设置附加到postgresql.auto.conf并创建一个standby.signal文件。
作者:藤井正雄<masao(dot)fujii(at)gmail(dot)com>
作者:西蒙·里格斯<simon(at)2ndquadrant(dot)com>
作者:Abhijit Menon-Sen <ams(at)2ndquadrant(dot)com>
作者:Sergei Kornilov <sk(at)zsrv(dot)org>
两个星期过去了,此提交尚未回滚。 好厉害 看来他们甚至都不会去。 太神奇了 目前尚不知道社区是否会决定再次朝任何方向改变行为,特别是因为距离4月postgresql 12的功能冻结发布尚有一段时间。 但是似乎我们将没有更多的recovery.conf。

所以发生了什么变化


首先,最重要的是,DBMS如果找到了recovery.conf文件,则将拒绝启动-这是专门为使用户使用许多旧指令之一而感到惊讶的原因,数据库为什么会忽略此文件中的配置。

旧的standby_mode设置已消失。 现在,它以及存在用于启用恢复模式的recovery.conf的事实,被两个文件(任何内容,通常为空)替换:

  • $ PGDATA / recovery.signal-意识形态后继standby_mode = off,将从归档恢复到配置中指定的位置;
  • $ PGDATA / standby.signal-分别为standby_mode = on。 我们将在所有副本上看到此文件。

如果数据库的启动过程找到了两个文件,则我们认为我们处于待机模式。

为了清楚起见,如果为了减少参数而更改板块:
旧的recovery.conf
PostgreSQL 12+ postgresql.conf
primary_conninfo
primary_conninfo
primary_slot_name
primary_slot_name
trigger_file
Promotion_trigger_file
recovery_min_apply_delay
recovery_min_apply_delay
recovery_target
recovery_target
recovery_target_name
recovery_target_name
recovery_target_time
recovery_target_time
recovery_target_xid
recovery_target_xid
recovery_target_lsn
recovery_target_lsn
recovery_target_inclusive
recovery_target_inclusive
recovery_target_timeline
recovery_target_timeline
recovery_target_action
recovery_target_action
restore_command
restore_command
archive_cleanup_command
archive_cleanup_command
recovery_end_command
recovery_end_command

您会看到几乎没有改变。 此刻(除了promove_trigger_file的promote_前缀唯一例外),所有新参数的命名都与旧参数一样,并且采用相同的可能值。 尽管实际上恢复目标的设置仍然存在变化。 我不知道以前是否有人使用过,但这是有记录的行为,可以同时指定多个recovery_target,recovery_target_lsn,recovery_target_name,recovery_target_time或recovery_target_xid。 举个例子

recovery_target_lsn = '1/1D9FEA00' recovery_target_xid = '5238954' 

实际上,来自recovery.conf的最后一行用于恢复。 这已不再可能,恢复目标应以最大值1表示。 但是,由于GUC基础结构的逻辑,您仍然可以多次指定相同名称的参数:

 recovery_target_lsn = '1/1D9FEA00' recovery_target_lsn = '1/16AC7D0' 

这是可以接受的,我们将恢复到最后指定的设置值。

而且,一般而言,这就是从PostgreSQL外部可见的更改所需要说明的全部内容。 pg_basebackup -R(--write-recovery-conf)保持原样并按预期进行,只是现在它将向postgresql.auto.conf中添加参数,而不是recovery.conf并创建一个standby.signal文件

不幸的是,当我说这些都是当前可见的所有更改时,这正是我的意思。 所有新参数仍设置为PGC_POSTMASTER,即只能在PostgreSQL启动时更改。 如前所述,这是开发人员社区的要求:首先,转移所有设置,然后再查看是否可以在运行的数据库上对其进行更改。 因此,现在PostgreSQL处在一个奇妙的发展阶段,旧的行为已经被打破,并且还没有带来更好的改变。

我已经发布了一个补丁该补丁将允许动态更改primary_conninfo和primary_slot_name。 让我们看看会发生什么。

抱歉,我打断了您的recovery.conf

UPD 2019年4月7日


在功能冻结版本12的最后一天,您可以进行总结。 发行版中不包括更改复制设置。 当然,这也是一个奇怪的故事。 很久以前,我作为基础的Simon Riggs补丁已经包含了在更改连接设置时重新启动walreceiver的编辑。 我在单独的补丁中选择了它们,并补充了文档和测试。 经过6个补丁更新和几个月的讨论之后,一个显而易见的事实突然出现:如果重新启动walreceiver,数据库将尝试切换为从restore_command恢复文件。 由任何原因关闭walreceiver触发的状态机行为都非常简单。 但是事实证明这是“我们不想要的东西”。 好吧,更早之前无法说? 好的,我以某种方式对其进行了重做,但是日历已经具有版本12的最终commitfest,因此没有人看到。 通常,这不是一件快速的事情,PostgreSQL中的修补程序确实可以做到。 但是,我有权利将自己包括在人员列表中,这要感谢在版本12 包括了史诗级的未完成的未完成的REINDEX

最后值得一提的是,有许多设置可以随时更改:archive_cleanup_command,promote_trigger_file,recovery_end_command,recovery_min_apply_delay

Source: https://habr.com/ru/post/zh-CN432918/


All Articles