提到国产数据库的高可用方案,绕不开 DM8 主备集群部署。很多单位从国外数据库迁到 DM8 之后,第一件事就是把主备集群搭起来,因为单实例跑在物理机器上,等于把所有鸡蛋放在一个篮子里,磁盘坏了、机房断电、操作系统崩溃,任何一项都能让业务直接停摆。我之前参与过好几个迁移改造项目,每次都会把主备集群部署作为交付清单里的必选项,今天就把整个部署过程做个复盘,从环境规划到配置文件,从初始同步到日常切换,把容易踩的坑一并写出来。这篇适合正在做 DM8 高可用方案的数据库工程师,也适合刚上手 DM8、想理解主备原理的运维新人。
DM8 主备集群并不复杂,但配置文件的细节非常多,一个 IP 写错、一个端口冲突、一个初始化参数不一致,都可能导致集群起不来或者同步中断。与其遇到问题再排查,不如把每个配置项背后的原因先搞清楚。
1. 为什么单实例跑业务的人,最后都补上了主备集群
1.1 一次数据库故障,足够让人记十年
很多 DBA 都经历过类似的场景:凌晨两三点被电话叫醒,某个核心业务系统的数据库起不来了,业务直接停摆,群里全是领导在问“还要多久”。单实例数据库不管硬件多稳定,总有你控制不了的故障点。磁盘阵列控制器坏了、双路电源同时跳闸、操作系统升级驱动异常、机房网络设备重启,任何一项都足以让一个运行了一两年的正常实例瞬间不可用。
DM8 本身再稳定,也挡不住宿主机层面的故障。数据库高可用解决的不是数据库本身的问题,而是承载数据库的整个物理环境的风险。主备集群的核心意义,就是让单台机器、单块磁盘不再成为唯一的故障点。这也是为什么很多单位在部署 DM8 时,无论业务规模大小,第一套高可用方案永远优先考虑主备集群。
1.2 主备集群到底是怎么“备”的
DM8 主备集群的核心机制可以概括为“实时归档 + 日志重放”。主库上的每次事务提交都会产生日志,这些日志会通过 MAL 链路实时发送到备库,备库不断应用这些日志,让自己的数据状态始终逼近主库的最新状态。主库一旦异常,备库可以在很短的时间内被提升为新主库,业务几乎感受不到底层发生了切换。
这里有两个术语经常出现在主备文档里:RPO 和 RTO。RPO 是恢复点目标,指的是数据最多丢多少;RTO 是恢复时间目标,指的是恢复业务需要多长时间。在 DM8 实时主备模式下,RPO 理论上为 0,也就是说主库上已提交的事务不会丢;RTO 则取决于故障检测时间加切换动作耗时,通常能做到秒级到分钟级。现在很多等保要求、业务连续性要求里都会明确写这两个指标,主备集群正好能命中这个需求。
还有一种容易被忽略的价值是“备库可读”。备库平时处于只读状态,可以开放给报表系统、查询平台使用,把一部分读压力从主库分流出去。我见过不少项目就是因为备库可读这一点,顺带把主库的慢查询问题缓解了不少,这是主备集群白送的红利。
1.3 主备集群和其他高可用方案怎么选
DM8 不止一种高可用方案,很多人在规划阶段就卡在选型上。除了主备集群,还有 DMDSC 共享存储集群、读写分离集群、MPP 分布式集群。我给一个自己的选型对照,方便你判断。
| 方案 | 核心特点 | 适用场景 | 成本与复杂度 |
|---|---|---|---|
| 主备集群 | 双机一主一备,日志实时同步,备库只读 | 绝大多数 OLTP 业务、中小型核心系统 | 成本低,无需共享存储,运维简单 |
| DMDSC 共享存储集群 | 多个实例共享同一套存储,并行提供服务 | 对性能和连续性要求极高的核心交易系统 | 依赖 SAN 等共享存储,硬件和运维成本高 |
| 读写分离集群 | 一主多从,主写从读,分摊查询压力 | 读多写少、报表查询重的业务 | 比主备多部署节点,数据延迟需关注 |
| MPP 分布式集群 | 数据分布到多个节点并行计算 | 海量数据分析、数据仓库类场景 | 节点多、部署复杂,不适合 OLTP 强一致 |
如果业务不是特别核心到需要实时双活,我一般都建议先用主备集群。理由很直接:部署模式成熟、不依赖昂贵的共享存储、切换动作可控、备库还能承担查询。很多项目一开始想上 DMDSC,评估完硬件成本之后还是老老实实回到主备,这个现象挺普遍的。
2. 动手前把这些准备做好,部署少走一半弯路
2.1 网络和端口规划
主备集群最少需要两台机器,一主一备。机器配置建议保持一致,不然切换后业务会感受到明显的性能落差,尤其是备库升主库的瞬间,差的机器可能直接被打垮。
网络规划上,生产环境我建议主备节点之间的 MAL 链路走独立的网卡或者独立的 VLAN。MAL 链路承担的是日志实时传输,数据量大、对网络抖动敏感,如果和业务流量挤在同一个交换机上,一旦业务高峰出现拥塞,日志传输延迟就会升高,极端情况下可能触发守护进程误判故障。
端口规划建议单独列一张表,不要随手写几个数字。下面是通用的规划方式:
| 用途 | 默认/常用端口 | 说明 |
|---|---|---|
| 数据库实例服务端口 | 5236 | 应用连接数据库使用 |
| MAL 通信端口 | 5336 / 5337 | 两个节点之间的日志传输链路 |
| 守护进程端口 | 5536 / 5537 | 守护进程之间以及监视器连接使用 |
注意 MAL 端口和实例端口不能冲突,两台机器的 MAL 端口与守护端口可以相同,也可以不同,只要保证每台机器本地端口不冲突即可。
2.2 操作系统侧的准备
DM8 支持多种 Linux 发行版,生产环境常见的中标麒麟、麒麟V10、CentOS 等都没问题。安装前先创建好用户和用户组,达梦官方约定俗成的做法是创建 dmdba 用户和 dinstall 用户组,所有数据库文件和安装文件都归属于这个用户。
还需要调整资源限制。打开 /etc/security/limits.conf,给 dmdba 用户设置文件句柄和进程数的上限,至少调大软硬限制到 65536 以上,比如:
dmdba soft nofile 65536 dmdba hard nofile 65536 dmdba soft nproc 65536 dmdba hard nproc 65536内核参数方面,共享内存、信号量这些一般默认值够用,但注意关闭透明大页或者设置为 madvise,避免数据库运行期间出现内存分配异常。防火墙方面,主备节点之间的实例端口、MAL 端口、守护端口必须放行,如果你不想关防火墙,就精确地把这几个端口加白名单。这个问题很基础,但我在现场遇到太多因为防火墙挡端口导致集群状态异常的案例了。
2.3 安装 DM8 并初始化两个实例
安装 DM8 软件本身不复杂,图形化或者静默安装都可以,安装包解压之后执行 DMInstall 脚本就行。这里有一个硬性要求:主备两个节点的 DM8 版本必须一致,包括小版本号。版本不一致会导致日志格式不兼容,轻则同步中断,重则备库根本起不来。我建议安装完成后先在两个节点分别跑一下select * from v$version;对比版本号,确认一模一样再继续。
安装完成后,初始化实例。dminit 命令初始化时有很多参数会影响数据文件格式,这些参数主备两侧必须完全一致,尤其是页大小、簇大小、字符集、大小写敏感这几个。下面是一个典型的初始化命令:
dminit PATH=/dm8/data INSTANCE_NAME=DM1 PORT_NUM=5236 PAGE_SIZE=8 EXTENT_SIZE=16 CHARSET=1 CASE_SENSITIVE=0PATH 指定数据目录,INSTANCE_NAME 是这个实例的名字,PORT_NUM 是数据库端口,PAGE_SIZE 是页大小,单位是 KB,生产环境常用 8 或 16;CHARSET 为 1 表示 UTF-8,CASE_SENSITIVE 为 0 表示大小写不敏感。你在备库初始化时,除 INSTANCE_NAME 和 PATH 外,其他参数必须和主库完全一致,否则后面还原备份集时会报“备份集不匹配”之类的错误。
3. 决定集群生死的,是这些配置文件
3.1 dm.ini 里的关键开关
每个实例有一个 dm.ini 文件,这是 DM8 最核心的配置文件。主备集群部署时,有几个参数必须重点关注。
首先是INSTANCE_NAME,这个必须和 dminit 时指定的实例名一致,后面 MAL 配置里也会引用它。然后是PORT_NUM,这是客户端连接的端口。最关键的开关是这两个:MAL_INI和ARCH_INI。
MAL_INI 表示是否启用 MAL 系统,主备集群必须置为 1,否则实例之间无法建立日志传输链路;ARCH_INI 表示是否启用归档配置,也必须置为 1。这两个参数关掉任何一个,主备集群都跑不起来。
还有一个参数ALTER_MODE_STATUS,建议设为 1。这个参数的作用是允许通过 SQL 语句手工切换数据库模式,测试阶段非常有用。生产环境如果担心误操作,可以设为 0 增加保护,但部署调试阶段开着能省不少事。
修改 dm.ini 之后必须重启实例才能生效。所以我的建议是:先把所有参数都改好,再统一重启,避免反复启停。
3.2 归档是怎么配的
开启归档有两种方式,一种是在 dminit 初始化时直接指定,另一种是实例启动后通过 SQL 动态添加。我习惯用 SQL 方式,因为不用重新初始化实例。
先在主库实例上执行以下步骤。把实例切换到 MOUNT 状态:
ALTER DATABASE MOUNT;然后添加归档配置。归档目录需要提前创建好,并确保 dmdba 用户有写权限:
ALTER DATABASE ADD ARCHIVELOG 'DEST=/dm8/arch, TYPE=arch, FILE_SIZE=1024, SPACE_LIMIT=10240';DEST 指定归档日志存放目录,TYPE=arch 表示本地归档,FILE_SIZE 是单个归档文件大小上限,单位是 MB,SPACE_LIMIT 是整个归档目录的空间上限,单位也是 MB。配置完成之后打开归档模式并回到 OPEN 状态:
ALTER DATABASE ARCHIVELOG; ALTER DATABASE OPEN;确认归档是否生效,可以查视图:
SELECT ARCH_MODE FROM V$DATABASE;返回值为已打开归档模式就说明成功了。归档对主备集群而言不只是用于恢复,它本质上是日志传输的源头。备库能够实时同步,靠的就是主库不断产生归档日志并通过 MAL 链路推送过去。
3.3 MAL 链路与 dmmal.ini
MAL 链路是主备节点之间传输日志的通道,配置文件是 dmmal.ini。这个文件在主备两台机器上都必须存在,内容除实例名和 IP 外基本对称。
一个典型的两节点 dmmal.ini 长这样:
MAL_CHECK_INTERVAL = 5 MAL_CONN_FAIL_INTERVAL = 5 [MAL_INST1] MAL_INST_NAME = DM1 MAL_HOST = 192.168.10.11 MAL_PORT = 5336 MAL_DW_PORT = 5536 [MAL_INST2] MAL_INST_NAME = DM2 MAL_HOST = 192.168.10.12 MAL_PORT = 5337 MAL_DW_PORT = 5537MAL_INST_NAME 必须和对应实例的 INSTANCE_NAME 完全一致,MAL_HOST 填本节点用于 MAL 通信的内网 IP,MAL_PORT 是日志传输端口,MAL_DW_PORT 是守护进程之间的通信端口。MAL_CHECK_INTERVAL 和 MAL_CONN_FAIL_INTERVAL 是链路检测参数,单位秒,一般默认 5 即可,不要设得太小,否则网络轻微抖动就被判定为故障。
配置容易踩的坑有两个。第一,MAL_HOST 不能写 127.0.0.1,必须写实际网卡 IP,而且两个节点互相要能 ping 通。第二,MAL_PORT、MAL_DW_PORT 不能和 dm.ini 里的 PORT_NUM 冲突,否则启动时端口被占用直接报错。
3.4 守护进程与 dmwatcher.ini
守护进程是主备集群的大脑,负责监控实例状态、执行故障切换、协调主备关系。它的配置写在 dmwatcher.ini 里,两个节点各有一份。
[DW_1] DW_TYPE = GLOBAL DW_MODE = AUTO DW_ERROR_TIME = 15 INST_RECOVER_TIME = 60 INST_ERROR_TIME = 15 INST_OGUID = 453331 INST_INI = /dm8/data/DM1/dm.ini INST_AUTO_RESTART = 1 INST_STARTUP_CMD = /dm8/bin/dmserverDW_TYPE 一般固定为 GLOBAL,表示全局守护配置。DW_MODE 有两个取值:AUTO 表示自动切换,MANUAL 表示手工切换。生产环境建议 AUTO,测试环境可以先 MANUAL,方便一步步观察状态变化。
DW_ERROR_TIME 是主库故障判定时间窗口,单位秒。超过这个时间主库没有响应,守护进程就判定主库故障并触发切换。这个值不能拍脑袋填,我建议结合监控软件的网络检测周期来设置,一般 10 到 30 秒比较合理。设太短,网络抖动会引发频繁切换;设太长,故障恢复时间就变长了。
INST_OGUID 是集群的唯一标识,可以在 DIsql 里执行SP_SET_OGUID(453331);来设置,两个节点必须一样。INST_INI 指向该节点 dm.ini 的绝对路径,INST_AUTO_RESTART 置为 1 表示实例异常退出后由守护进程自动拉起,INST_STARTUP_CMD 指向 dmserver 启动程序。
除了这些,还要准备一个 dmmonitor.ini,这是监视器的配置文件。监视器相当于操作员的控制台,用来查看集群状态、执行手工切换命令。一个典型的配置:
MON_DW_CONFIRM = 1 MON_LOG_PATH = /dm8/log [DMON1] MON_DW_IP = 192.168.10.11 MON_DW_PORT = 5536 [DMON2] MON_DW_IP = 192.168.10.12 MON_DW_PORT = 5537MON_DW_CONFIRM 置为 1 表示这个监视器是确认监视器。确认监视器在自动切换中承担仲裁作用,防止出现脑裂,生产环境强烈建议配置。
4. 从备份到拉起主备,完整部署流程实操
4.1 主库全量备份
配置文件的准备工作完成之后,开始真正的部署动作。第一步是在主库上做一次全量备份,这个备份集将用于初始化备库。
在 DIsql 里执行:
BACKUP DATABASE FULL BACKUPSET '/dm8/bak/bak_db1';执行成功后在 /dm8/bak 目录下会生成一个备份集目录,里面包含数据文件的完整镜像。做这个备份的目的是让备库有一个和主库一致的数据起点,因为主备同步不是从零开始灌数据,而是先把备库恢复到主库的某个时间点,然后通过日志增量追上最新状态。
注意备份目录要放在备库也能访问到的地方。如果你有共享存储,直接放到共享路径最省事;没有共享存储,就通过 scp 等方式把整个备份集目录拷到备库服务器。拷完之后建议对比一下文件大小,确认复制完整,别因为网络中断搞了个半残备份过去。
4.2 备库还原与恢复
备库上的数据文件通过 dmrman 工具从备份集还原。先确保备库的数据目录是干净的,如果之前初始化过实例,最好把数据目录下的文件清空,否则还原时会因为目录非空而报错。
使用 dmrman 执行还原:
dmrman CTLSTMT="RESTORE DATABASE '/dm8/data/DM2/dm.ini' FROM BACKUPSET '/dm8/bak/bak_db1'"还原成功后再做恢复:
dmrman CTLSTMT="RECOVER DATABASE '/dm8/data/DM2/dm.ini' FROM BACKUPSET '/dm8/bak/bak_db1'"RESTORE 是把备份中的数据文件“铺”到备库目录,RECOVER 是把备份期间产生的日志应用进去,让备库数据一致地恢复到主库备份结束的那个时间点。这两个命令都完成后,备库的基础数据就和主库对得上了。
插一句,dmrman 也可以通过交互式方式进入,然后逐条执行 RESTORE 和 RECOVER。交互式的好处是命令执行过程看得更清楚,出错时方便逐条排查,脚本化部署则用 CTLSTMT 更方便。
4.3 OGUID 与启动顺序
备库数据准备好之后,开始配置实例和启动。这里启动顺序非常关键,顺序错了会导致守护进程报错。
先启动主库实例。以 DM1 为例,执行:
dmserver /dm8/data/DM1/dm.ini也可以先把实例注册成系统服务,然后通过服务启动,后面统一讲。实例起来之后,用 DIsql 登录并设置 OGUID:
SP_SET_OGUID(453331);这个函数只能在 MOUNT 状态下执行。如果实例已经在 OPEN 状态,需要先执行ALTER DATABASE MOUNT;再设置。OGUID 设置好之后,主库可以转回 OPEN 状态:
ALTER DATABASE OPEN;再启动备库实例。备库同样要先启动到实例,登录 DIsql,执行ALTER DATABASE MOUNT;然后设置相同的 OGUID:
SP_SET_OGUID(453331);注意备库不要提前打开到 OPEN 状态,保持 MOUNT,后续由守护进程根据集群状态自动处理。SP_SET_OGUID 这个操作每个实例只能执行一次,执行之后无法直接修改,除非重新初始化实例。所以设置时一定要确认数字无误,别随手敲错又发现改不回来。
4.4 启动守护进程和监视器
主备实例都准备好后,启动两个节点的守护进程。先启动主库所在节点的 dmwatcher,再启动备库所在节点的 dmwatcher。
dmwatcher /dm8/data/DM1/dmwatcher.inidmwatcher /dm8/data/DM2/dmwatcher.ini守护进程启动后会自动开始检测实例状态、建立主备关系。接着启动监视器:
dmmonitor /dm8/data/dmmonitor.ini进入监视器命令行后,先执行show命令查看集群全局状态。正常情况下会看到两个实例都在线,主库状态为 OPEN,备库状态为 MOUNT 或者已经转为只读的 Standby 模式。如果状态一直是 INVALID,说明配置有问题,需要结合日志排查。
这里我强烈建议把 dmserver、dmwatcher、dmmonitor 都注册成系统服务。DM8 安装目录的 script/root 下提供了服务安装脚本,用法大致是:
/dm8/script/root/dm_service_installer.sh -t dmserver -p DM1 -dm_ini /dm8/data/DM1/dm.ini /dm8/script/root/dm_service_installer.sh -t dmwatcher -p DM1 -watcher_ini /dm8/data/DM1/dmwatcher.ini /dm8/script/root/dm_service_installer.sh -t dmmonitor -p DMON -monitor_ini /dm8/data/dmmonitor.ini注册成服务之后,不仅可以用 systemctl 统一管理,更重要的是操作系统重启后守护进程能自动拉起来。很多生产事故的二次伤害就来自重启集群后没人记得手动启动守护进程。
4.5 数据同步验证
集群起来之后,不要急着接业务,先做一轮数据同步验证。在主库上建一张测试表,插入几行数据,提交事务:
CREATE TABLE TEST_SYNC (ID INT, NAME VARCHAR(20)); INSERT INTO TEST_SYNC VALUES (1, 'PRIMARY_NODE'); COMMIT;然后登录备库查询:
SELECT * FROM TEST_SYNC;能在备库查到这条数据,说明主库日志已经通过 MAL 链路传到备库并完成重放,同步链路是通的。如果查不到,说明同步还没建立起来,需要检查归档状态、MAL 链路和守护进程状态。
再做一次写入隔离测试,在备库上执行 insert。正常情况下会报错,因为备库是只读的。这一步验证备库的只读属性是生效的,防止后续应用误连到备库写坏数据。
5. 主备切换和灾后重建,建议每个季度演练一次
5.1 手动切换操作流程
主备集群不只是搭完就完事,切换操作必须熟练。手动切换的目的是主动运维,比如主库所在服务器需要硬件维护、系统升级,这时主动把业务切到备库,整个过程可控、无感知。
在 dmmonitor 命令行里执行切换命令,将指定实例切换为新主库。假设当前主库是 DM1,要把主库角色切给 DM2:
switchover DM2;执行之后监视器会先检查 DM1 和 DM2 的状态,确认都正常后开始角色互换。切换完成后再次执行show,应该看到 DM2 变成主库,DM1 变成备库。此时应用连接需要重新指向新的主库地址,如果前面配了 VIP 之类的虚拟地址,则需要把 VIP 一并切换到新主库。
手动切换前要确认几件事:当前主备状态都是健康、没有未提交的长事务、备库日志应用没有堆积。如果备库延迟很大,切换过去会丢数据吗?实时主备模式下备库实时应用日志,正常情况下不会堆积,但网络故障或备库负载过高时会有延迟。保险起见,切换前先在监视器里查看备库的日志应用状态,确认没有明显延迟再切。
5.2 自动故障切换与脑裂防护
自动切换是 AUTO 模式下的核心能力。当主库在 DW_ERROR_TIME 时间内没有响应,守护进程会判定主库故障,随后协调备库接管主库角色,整个过程不需要人工干预。
听起来很美好,但自动切换有一个必须重视的风险:脑裂。所谓脑裂,就是主库并不是真的宕机,而是由于网络分区导致主备之间互相联系不上。主库还活着,备库却在守护进程的协调下把自己升成了主库,于是系统里出现了两个主库,各自接收业务写入,数据自然就分叉了。
DM8 的防脑裂机制依赖确认监视器。确认监视器会持续监控两个节点的状态,当备库想要升级为主库时,需要向确认监视器确认主库确实不可用。所以生产环境必须配置 MON_DW_CONFIRM=1,而且确认监视器所在的主机要稳定,最好放在独立的机器或者至少不要放在主库所在的节点上。
DW_ERROR_TIME 的设置也直接影响自动切换的准确率。这个值太小,网络闪断就会引发切换;太大,故障恢复时间又太长。我建议结合你现有的监控系统报警周期来定,比如监控系统 10 秒一个探测周期,DW_ERROR_TIME 设在 15 到 30 秒就比较平衡。
5.3 切换后的备库重建流程
每次切换之后,原来的主库经过故障修复,角色变成了备库,但它身上的数据可能已经落后于新主库。如果故障期间旧主库还有部分日志没传出去,它的数据状态是落后且有分歧的,不能直接继续当备库。
常规操作是把旧主库重新做一遍备库。流程和第一次部署类似:先清理旧主库的数据目录,用新主库做一次全量备份,把备份集恢复到旧主库机器,重新配置好 dmmal.ini 和 dmwatcher.ini,设置 OGUID,启动实例并加入集群。
很多项目第一次部署时一步到位,但切换演练后发现不会重建备库,导致故障后主备集群很长一段时间处于单点运行状态。这个流程最好也写进运维手册,每个季度演练一次,真到出事的时候才能从容应对。
6. 常见问题排查表与避坑心得
6.1 故障现象与处理速查
| 现象 | 可能原因 | 处理方法 |
|---|---|---|
| 备库一直处于 MOUNT 状态不同步 | 归档未开启、OGUID 不一致、MAL 链路不通 | 检查主库归档模式,核对两节点 OGUID,ping 测试 MAL 端口 |
| 守护进程启动后频繁退出 | dmwatcher.ini 中 INST_INI 路径错误或 OGUID 未设置 | 修正路径,DIsql 中执行 SP_SET_OGUID |
| 主备库显示 INVALID | dm.ini 中 MAL_INI 或 ARCH_INI 未置 1 | 修改参数并重启实例 |
| 备库查询不到主库刚提交的数据 | 同步存在延迟、MAL 链路拥堵、归档目录满 | 查看归档目录空间,检查网络质量,观察日志应用进度 |
| 还原备份集报不匹配 | 主备初始化参数不一致,如页大小、字符集 | 重新初始化备库,参数与主库保持一致,再还原 |
| 自动切换没有生效 | DW_MODE 不是 AUTO、确认监视器未配置 | 修改 DW_MODE,配置确认监视器并重启 |
| 切换后应用连不上数据库 | 连接地址还指向旧主库 | 切换 VIP,或修改中间件数据源指向新主库 |
排查问题时,先看 dmserver 日志,再看 dmwatcher 日志,最后看 dmmonitor 输出。日志路径一般在实例数据目录下的 log 目录里,格式如 dm_DM1_20250101.log。日志里会直接写出错误原因,比如端口冲突、OGUID 不匹配、网络不可达,定位效率比瞎猜高得多。
6.2 独家避坑心得
第一,两个节点的配置文件要 diff 一遍再启动。我每次部署都会把 dmmal.ini、dmwatcher.ini 分别从两个节点取出来做对比,除了 IP、实例名、路径这些本来就该不同的项之外,其他参数必须完全一致。很多时候集群起不来,就是因为备库的 dmwatcher.ini 里某个参数漏改了,肉眼又不容易发现。
第二,备份集拷贝到备库之前必须检查完整性。我遇到过备份文件拷了一半以为拷完了,结果一执行 RESTORE 就报备份集损坏。现在我的习惯是拷贝完立刻执行du -sb对比源端和目标端的字节数,一致了再动下一步。
第三,SP_SET_OGUID 一定要在 MOUNT 状态执行,而且只能执行一次。这个函数执行时机不对会报错,执行两次则直接拒绝执行。初始化脚本里我通常把设置 OGUID、修改模式、打开数据库放在一个完整的执行序列里,避免人工在多个窗口切换时搞错顺序。
第四,不要把 DM1、DM2 这种实例名写进应用连接串。应用应该走 VIP 或者中间件配置的数据源,主备切换只影响数据库层,应用层不应该感知到实例名的变化。很多项目切换后业务恢复慢,卡就卡在应用连接串里的 IP 还是旧的。
第五,备份和归档监控必须纳入日常值班。主备集群最怕的不是主库故障,而是备库其实已经断同步很久了,等到主库真挂了才发现备库根本接不住。我见过某项目备库归档目录写满,同步停了三天都没人发现,这种情况下谈高可用就是自欺欺人。
我个人在实际操作中体会最深的一点是:主备集群部署本身不难,难的是养成“平时按切换标准演练、故障时按手册执行”的习惯。很多问题第一次遇到时会觉得莫名其妙,但只要把配置文件的逻辑吃透,把日志读明白,八成问题都能在十分钟内定位。希望这篇梳理能帮你把 DM8 主备集群从部署到维护的完整链路走通,少在半夜被电话叫醒几次。