首页 > 数据库 > 数据库开发技术 > 主从环境调整参数引发的故障思考
来自同事分享的一个案例:主从环境下修改某几个参数时引发数据库服务启动失败
复现备库启动失败的操作流程如下:
前提:在一套一主两备的集群中,max_worker_process参数由16改为8时,3个节点先关闭主库和异步备库2,保持同步备库1开启:
1.修改主库的max_worker_process为8并重启,观察备库1的日志如图1
2.修改备库2的max_worker_process为8并重启,观察备库2日志如图2
3.修改备库1的max_worker_process为8并重启,重启正常(无图)
图1:
图2:
关注上面图片中的两处错误文本信息:
DETAIL: max_worker_process = 8 is a lower setting than on the primary server,where its value was 16.
LOG:00000:recovery has paused
为什么备1的流复制发生中断,备2为什么重启失败呢?
从测试的过程中,我们可以感觉到,max_worker_process除了可能存储在postgresql.conf、postgresql.auto.conf这两个配置文件中之外,似乎还会存储在某个位置?

经过一番探索,猜测得到了验证:一共有5个类似的参数,它们会存储在控制文件中。
备库控制文件中的参数值,会同步主库控制文件的值。如果主库控制文件更新的时候,备库处于离线状态,则控制文件无法及时更新,下次启动读取的依旧是上一次更新的值。因此上面测试中备库1可以直接修改参数重启,而备库2修改参数重启会报错。
而另外一个错误提示(recovery has paused),则是14版本开始做的优化,在此之前备库会宕机。
步骤1主库修改参数值时,仍有运行中的standby节点(备库1)未重启让生效参数,此时主库修改的参数新值同步到备1控制文件(备库开了hot_standby),但备1的配置文件未修改,此时备1的参数值其实处于“脏值”状态,所以PG自动暂停了备1节点的服务,而步骤3重启备1则可恢复正常。
而步骤2备2直接修改参数值重启会失败,主要是受hot_standby为on的影响,其控制文件记录的参数值是主库修改参数之前的旧值,而主库修改参数重启之后检测到参数值不一致,所以启动失败,此时可以先关闭hot_standby为off,修改新值成功后再设置为on。
修改max_connections、max_worker_processes、max_wal_senders、max_locks_per_transactions、max_prepared_transactions这五个参数时需要注意:
这5个参数备库需要等于或大于主库,所以生产环境如果是调大值,需要先调备库再调主库
如果是减小参数,需要先调主库重启生效或,再将在线的备库逐一重启调整生效。
但如果已经将主备集群的全部节点关闭,且主库已经调整完成并启动,则解决方案如下:
方法1:备库节点先不改配置,直接启动后再修改配置,最后重启生效;
方法2:备库节点将hot_standby参数改为off,修改启动后再调整hot_standby参数为on,最后重启数据库
原文作者:象楚之行;如有侵权,请联系管理员删除。