KingbaseES 高可用集群故障恢复实践与运维落地

1 阅读7分钟

正文开始——

在企业核心业务系统里,数据库高可用直接关系到业务能不能连续运行、数据安不安全。KingbaseES 作为国产自主可控的企业级数据库,在金融、政务、能源等关键行业里用得越来越多。实际运维过程中,服务器宕机、网络中断、参数配置不合理、人为误操作、磁盘异常、数据块损坏这些问题都可能出现。能不能快速、规范、安全地把故障恢复过来,是衡量 DBA 和运维人员能力的关键。

本文把读写分离集群故障恢复、物理备份故障恢复、数据应急恢复这三块最核心的内容梳理出来,把故障判断、排查命令、自动和手动恢复流程、典型场景处理方法、实操命令、参数配置都讲清楚。

一、先搞清楚:KingbaseES 故障恢复基础

1.1 什么是故障恢复

简单说,故障恢复就是把硬件、网络、数据库实例和数据,从出错的状态,用技术手段恢复到正常、一致、完整的状态。我们平时说的故障恢复,主要针对数据库本身,目标很明确:把业务中断时间(RTO)和数据丢失量(RPO)降到最低。

1.2 故障恢复为什么重要

数据库是整个业务系统的数据中心,它稳不稳定、数据完不完整,直接决定业务能不能用。故障恢复是数据库高可用的最后一道防线,不管是节点挂了、数据坏了、备份失效了,还是集群裂了,都得靠恢复流程把服务拉回来,避免业务长时间停掉、数据彻底丢了。

1.3 三类最常见的故障恢复场景

官方文档里把恢复分成三大类,基本覆盖了生产环境所有问题:

  1. 读写分离集群故障恢复:主备节点挂掉、集群分裂、出现多主或者没有主库、进程异常、网络断了、存储出问题;
  2. 物理备份故障恢复:sys_rman 配置不对、WAL 归档失败、内存不够导致备份中断、参数配置不合理;
  3. 数据应急恢复:数据误删、表或库被误删、数据块损坏、数据分叉需要回退到历史时间点。

1.4 几个必须懂的专业词

  • 主节点:对外提供读写服务的核心节点;
  • 备节点:只提供读服务或者做灾备的节点;
  • repmgr:集群管理工具,管主备切换、节点状态、集群监控;
  • kbha:高可用监控进程,负责巡检和自动拉起故障进程;
  • sys_securecmdd:集群节点之间安全免密通信的服务;
  • RTO:故障后恢复业务的时间;
  • RPO:故障后最多能接受丢失多少数据。

二、核心重点:读写分离集群故障恢复

KingbaseES 读写分离集群是生产里最常用的架构,主库负责写,备库负责读,还能自动负载均衡。集群故障分两种:能自动恢复的,和必须手动处理的。自动恢复能应付大部分常规问题,复杂场景比如多主、全节点故障,就必须手动一步步来。

2.1 恢复之前先做一件事:检查服务器状态

不管恢复什么,第一步必须确认服务器本身没问题,不然恢复命令执行了也没用。官方给出六项必查内容,我们在运维里要养成习惯:

  1. 网络:ping 集群信任地址,确保能通;
  2. 内存:用 free -h 看一下,剩余内存够数据库运行;
  3. 磁盘:df -h 看空间,再试着建文件、写内容,确认读写正常;
  4. 防火墙:查看 firewalld 状态,确保数据库端口和 8890 端口放开;
  5. 免密:用 ssh 或者 sys_securecmd 连其他节点,确认免密没坏;
  6. 定时任务:查看 /etc/cron.d/KINGBASECRON,确保 kbha 的定时任务在运行。

这些检查做完,再进入下一步,能少走很多弯路。

2.2 自动故障恢复:配置和能处理的场景

自动恢复靠 repmgr.conf 配置,文件在 ${install_dir}/kingbase/etc/ 下面,每个节点都要配,改完重启集群才能生效。

核心配置就两行:

recovery = automatic
# 或者
recovery = standby

automatic 是节点故障后尽量自动恢复;standby 是备库故障能自动恢复,主库故障直接切主,原主库不自动恢复。

官方文档里列出了能自动恢复的场景,我们日常遇到的大部分问题都在里面:

  • 主库停库、掉电、重启:备库自动升主,原主恢复后尝试重新加入;
  • 备库停库、掉电、网络断了:主库自动尝试恢复,基本不影响业务;
  • 进程被杀死:repmgrd 挂了 kbha 会 5 秒拉一次,kbha 挂了 crond 每分钟拉一次;
  • 存储故障:主库存储坏了自动切主,备库存储坏了自动把同步复制改成异步;
  • 数据块损坏:主库出现坏块,会自动从备库拿正常块修复,应用等修复完再返回。

这里有个小经验:网络丢包 30% 以内集群基本没感觉,丢包太严重才会触发断连和恢复。

2.3 手动故障恢复:按步骤来,不乱操作

自动恢复搞不定的,比如多主、全节点挂了、集群裂脑,就必须手动恢复。官方给出标准流程:先排查状态、确认是什么场景、备份 data 和日志、执行恢复、最后验证。

2.3.1 故障判断用这 8 条命令

所有集群异常,都靠这几条命令定位,我们在现场排障也是按这个来:

# FC-1 看集群整体状态
repmgr cluster show

# FC-2 看repmgrd服务状态
repmgr service status

# FC-3 看数据库进程是否存在
ps -ef | grep kingbase

# FC-4 看repmgrd进程
ps -ef | grep repmgrd

# FC-5 看kbha进程
ps -ef | grep kbha

# FC-6 看安全通信进程
ps -ef | grep sys_securecmdd

# FC-7 看是不是主库(没有standby.signal就是主库)
ls $data_path/standby.signal

# FC-8 看流复制状态
ksql -h 主库IP -U system -d test -c "select * from sys_stat_replication;"

2.3.2 集群最常见 7 种异常场景

根据上面命令的结果,可以精准判断集群出了什么问题:

  1. FS001:所有节点挂了,只有一个主库;
  2. FS002:所有节点挂了,出现多个主库;
  3. FS003:部分节点挂了,活着的节点里只有一个主库;
  4. FS004:部分节点挂了,活着的节点里有多个主库;
  5. FS005:部分节点挂了,活着的全是备库,没有主库;
  6. FS006:部分节点挂了,挂掉的节点里有主库;
  7. FS008:所有节点都活着,但出现双主或者多主。

2.3.3 恢复用的 5 条核心命令

官方把恢复命令封装成 FR 系列,现场直接用就行:

FR-1:多主场景先判断谁是真正的主库 多主是最危险的状态,必须先选出正确的主库,判断依据三个:

  1. 时间线更大的;
  2. WAL 日志 LSN 更大的;
  3. 数据量更大的。

命令:

-- 运行中查时间线
select timeline_id from sys_control_checkpoint();

-- 运行中查LSN
select sys_current_wal_lsn();

-- 查看数据库大小
select sys_size_pretty(sys_database_size(oid)) from sys_database;

停机状态可以用 sys_controldata -D $data_path 查看。

FR-2:全节点故障单主,一键启动集群

sys_monitor.sh start

FR-3:故障节点重新加入集群

sys_ctl -D $data_path stop
repmgr -h 新主IP -U esrep -d esrep node rejoin --force-rewind

FR-4:重新做备库(rejoin 失败时用)

sys_ctl -D $data_path stop
repmgr -h 新主IP -U esrep -d esrep -D $data_path standby clone -F --fast-checkpoint
sys_ctl -D $data_path start
repmgr standby register -F

FR-5:恢复完一定要验证状态

repmgr cluster show
repmgr service status
ksql -h 主库IP -U system -d test -c "select * from sys_stat_replication;"

标准结果:只有一个主库,所有节点 running,repmgrd 没有暂停,流复制正常。

2.3.4 不同场景怎么恢复

  • FS001 全节点故障单主:用 FR-2 启动,再 FR-5 验证;
  • FS002 全节点故障多主:FR-1 选主→启动新主→其他节点 FR-3→FR-5;
  • FS003 部分故障单主:故障节点 FR-3,失败就 FR-4,再验证;
  • FS004/FS008 多主:FR-1 选主→其他节点停库→FR-3 或 FR-4→验证;
  • FS005/FS006 无主 / 故障节点有主:把故障主库启动→其他节点 FR-3→验证。

这些步骤都是官方标准流程,我们在实际运维中直接照流程走,不会出问题。


三、物理备份故障恢复:备份不能断

物理备份用 sys_rman,是数据安全的底线。备份一失败,遇到灾难就没法恢复,所以备份故障必须快速处理。

3.1 常见备份故障场景

官方文档总结了几类:

  1. repo_ip 配置错了,没指向备份节点本机;
  2. 系统参数不对,比如 remove_ipc、share_buffer 设置不合理;
  3. 内存不够,OOM 把 rman 进程杀了;
  4. WAL 归档没开,或者路径错了;
  5. client_idle_timeout 设置太小,备份连接超时断开。

3.2 故障处理方法

  • 报错 repo_ip 必须在本地:改 sys_backup.conf,把 repo_ip 指向本机;
  • 参数报错:修改 /etc/systemd/logind.conf 里 RemoveIPC=no,调整 sysctl.conf 的共享内存;
  • OOM:加内存,或者把备份放到半夜业务低峰期;
  • 归档失败:开 archive_mode=ON,配置正确归档命令,重启数据库;
  • 连接超时:关掉 client_idle_timeout,或者升级版本。

核心修复命令:

vi $data_path/kingbase.conf
archive_mode = ON
archive_command = 'sys_rman archive-push %p'
sys_ctl -D $data_path restart

备份是底线,宁可多查一遍,不要带着问题跑。


四、数据应急恢复:数据坏了怎么救

数据应急恢复是最后一道防线,针对误删、数据块损坏、数据分叉这些紧急情况。

4.1 适用场景

  • delete 删数据、drop 删表、drop 删库;
  • data 目录被误删;
  • 需要回退到历史时间点;
  • 数据块损坏,查询报错。

4.2 能不能恢复,看这个矩阵

官方给出最实在的结论:有备份 + 有日志,就能不丢数据;没备份,基本救不回来。

  • 物理备份可用 + WAL 齐全:PITR 恢复,不丢数据;
  • 只有备份没有日志:恢复到备份时间点;
  • 没备份:数据彻底丢,无法恢复。

4.3 数据块损坏怎么处理

数据块损坏是最头疼的问题,官方给出三种恢复方式:

  1. 主备集群自动修复:主库坏块从备库同步正常块;
  2. 用物理备份恢复;
  3. 用离线工具修复。

应急时可以用两个参数临时抢救数据:

ignore_checksum_failure:忽略校验和错误

set ignore_checksum_failure = on;
select * from 损坏表;

只对校验和损坏有用,块头坏了没用。

zero_damaged_pages:把坏块清零,库能继续用

set zero_damaged_pages = on;
select count(*) from 损坏表;

风险是坏块数据会丢,vacuum full、写入还可能覆盖磁盘,只能应急用,用完马上关。

4.4 误删数据恢复思路

  1. 先停业务写入,别覆盖数据;
  2. 看物理备份和 WAL 日志齐不齐;
  3. 齐全就做 PITR 时间点恢复;
  4. 有日志没备份,用 WalMiner 解析日志找回数据;
  5. 啥都没有,恢复不了。

五、生产环境运维经验

结合官方指南和实际运维,给大家几条实在建议:

  1. 集群一律配成 automatic 自动恢复,减少人工操作;
  2. 每天物理备份,实时开 WAL 归档,保留多份备份;
  3. 日常巡检就用那几条 FC 命令,看集群、进程、复制状态;
  4. 每个月模拟一次主库挂了、多主、坏块,练熟恢复流程;
  5. 故障先备份 data 和日志,再动手恢复,别越修越坏;
  6. 那两个坏块应急参数,只用在紧急时刻,恢复完立刻关掉。

六、总结

KingbaseES 高可用故障恢复,其实就是三件事:集群故障按流程恢复、备份故障及时修复、数据故障尽力抢救。整套体系官方都给出了标准方案,从自动恢复到手动处理,从命令到参数,都很完整。

对 DBA 和运维来说,不用追求花里胡哨的技巧,把官方流程记熟、命令练熟、场景判断准,遇到故障按步骤来,就能保证业务快速恢复、数据尽量不丢。

生产环境最重要的还是预防:配置合理、备份到位、日常巡检做好,从根源上减少故障。