ORA-16047 根本原因是 DGID 不匹配,需先确认主备库 DB_UNIQUE_NAME 是否唯一且与 LOG_ARCHIVE_DEST_n 中配置严格一致(大小写敏感),再确保主备两端均正确配置 log_archive_config 参数,缺一不可。
ORA-16047 报错时,先确认 DB_UNIQUE_NAME 是否重复
看到 ora-16047: dgid mismatch between destination setting and target database,基本可以断定是主备库 db_unique_name 冲突或未正确注册。这个错误不是网络不通、归档没开,而是 dg 的身份校验直接失败了。
在备库执行:SELECT DB_UNIQUE_NAME FROM V$DATABASE;
再在主库查它的 LOG_ARCHIVE_DEST_n 配置:SHOW PARAMETER LOG_ARCHIVE_DEST_2(假设备库走的是 DEST_2)
重点看输出里 DB_UNIQUE_NAME=xxx 这一项,必须和备库当前值严格一致(大小写敏感)。
- 如果备库查出来是
dg1,而主库LOG_ARCHIVE_DEST_2里写的是DB_UNIQUE_NAME=dg2,那就直接冲突 - 如果主备都显示
dg1,那属于严重配置错误——DG 要求主备DB_UNIQUE_NAME必须不同 - 单实例改完后重启生效;RAC 环境下改完还必须同步 OCR,否则
srvctl start会找错 SPFILE 路径
单实例数据库修改 DB_UNIQUE_NAME 的安全操作流程
单实例改 DB_UNIQUE_NAME 表面简单,但漏掉一步就可能启动失败。
执行顺序不能颠倒:
- 确保数据库处于
MOUNT或OPEN状态(不能是NOMOUNT) - 运行:
ALTER SYSTEM SET DB_UNIQUE_NAME='new_name' SCOPE=SPFILE; - 关闭数据库:
SHUTDOWN IMMEDIATE - 重新启动:
STARTUP
注意:SCOPE=SPFILE 是必须的,因为 DB_UNIQUE_NAME 是静态参数,无法用 SCOPE=BOTH 在线修改。改完不重启,新值不会生效,V$DATABASE 仍显示旧名。
RAC 环境下 DB_UNIQUE_NAME 修改后节点启动失败的根源
RAC 改 DB_UNIQUE_NAME 后,一个节点能启、另一个启不了,大概率是 OCR 没同步更新。
OCR 里存着数据库资源的元数据,包括 DB_UNIQUE_NAME 和 SPFILE 路径。你改了 SPFILE 里的值,但 srvctl 启动时仍按 OCR 记录的旧名去找文件,比如:
OCR 记录:Spfile=+DATA/dave/spfiledave.ora
你实际改成了 dave_st,但 OCR 还是 dave,于是报错:ORA-01565: error in identifying file '+DATA/dave/spfiledave.ora'
- 先用
srvctl config database -d <db_name></db_name>查 OCR 当前记录的Database unique name - 用
srvctl modify database -d <db_name> -u <new_unique_name></new_unique_name></db_name>更新 OCR - 再确认所有节点的 SPFILE 路径是否真实存在且可读(特别是 ASM 路径权限)
- 最后统一用
srvctl start database -d <db_name></db_name>启动,别用 SQL*Plus 手动启
log_archive_config 必须双向配置,否则 DGID 校验照样失败
只改 DB_UNIQUE_NAME 不够,log_archive_config 必须在主备两端都配全。这是最容易被跳过的一步。
主库要告诉自己:“我信任这些备库”,备库也要告诉自己:“我也信任主库和其他备库”。否则主库发日志时,发现目标不在自己的 DG_CONFIG 列表里,直接拒绝。
- 主库执行:
ALTER SYSTEM SET log_archive_config='DG_CONFIG=(primary_db,standby_db)' SCOPE=BOTH; - 备库执行:
ALTER SYSTEM SET log_archive_config='DG_CONFIG=(primary_db,standby_db)' SCOPE=BOTH;(顺序无关,但列表必须完全一致) - 如果有多套备库(如级联 DG),所有库名都要列进两边的
DG_CONFIG,缺一不可 - 改完立即生效,无需重启,但建议用
SELECT DEST_ID, STATUS, ERROR FROM V$ARCHIVE_DEST_STATUS;验证状态是否变回 VALID
真正麻烦的从来不是改一个参数,而是改完之后忘了 OCR、忘了 log_archive_config、忘了大小写——这三个点卡住,DB_UNIQUE_NAME 改得再对也没用。











