RMAN默认跳过无变更的只读表空间,因其比对数据文件头SCN(checkpoint_change#与last_change#相等)判定未修改;需用BACKUP FORCE DATABASE或BACKUP TABLESPACE强制备份,或显式指定SKIP READONLY才跳过。
rman 不是“无法”备份只读表空间,而是默认跳过它——这不是故障,是设计行为;能否备份、是否跳过,取决于你用的是什么命令、有没有开优化、以及表空间当前状态是否真为 read only。
BACKUP DATABASE 默认包含只读表空间,但会跳过已确认无变更的只读数据文件
RMAN 执行 BACKUP DATABASE 时,只要表空间状态是 READ ONLY 且其数据文件头的 checkpoint_change# 与 last_change# 相等(即自设为只读后未发生任何 SCN 推进),就会直接跳过该数据文件。
这跟“备份优化”无关,是 RMAN 内置的变更判定逻辑。
- 这个跳过动作在日志里通常显示为:
skipping datafile ... because it is read-only - 它不依赖
CONFIGURE BACKUP OPTIMIZATION ON,哪怕你关了优化,这个跳过依然发生 - 真正影响“是否纳入备份集”的,是命令层级的显式控制,不是配置项
CONFIGURE BACKUP OPTIMIZATION ON 实际不控制只读表空间
很多人误以为开了这个就自动跳过只读表空间,其实不是:
-
BACKUP OPTIMIZATION只对“已备份过、且自上次备份以来未修改”的可写数据文件生效 - 只读表空间的数据文件压根不参与该判断流程——RMAN 先按只读状态单独处理,根本不到优化比对那步
- 验证方式:执行
SHOW ALL查看当前配置,再手动运行BACKUP DATABASE,观察日志是否仍有skipping提示;如果还有,说明不是优化配置的问题,而是命令本身没干预
为什么加了 SKIP READONLY 还是没跳过?常见状态错位
SKIP READONLY 必须满足三个硬条件才真正生效:
- 表空间状态必须是
READ ONLY(不是READ WRITE或OFFLINE) - 数据文件状态必须是
AVAILABLE(查dba_data_files.status) - 命令必须写在
BACKUP DATABASE主语句后,不能嵌套在脚本块或子命令中
容易踩的坑:
- 表空间刚切为只读,但事务还没完全提交,
v$tablespace.status显示仍是READ WRITE - 数据文件被误设为
OFFLINE,RMAN 默认跳过离线文件,但提示语是skipping offline datafile,和只读无关 - 脚本里写了
BACKUP DATABASE PLUS ARCHIVELOG SKIP READONLY,但前面有CONFIGURE EXCLUDE FOR TABLESPACE 'XXX',而该表空间名拼写大小写不一致(Oracle 默认大写,引号内小写会失效)
如何确认只读表空间到底进没进备份集
别信日志里的“skipping”字样——有些版本把 SKIP READONLY 的实际跳过记录藏在 debug 模式下。
最可靠的方式是查视图:
- 查当前只读表空间:
SELECT tablespace_name FROM dba_tablespaces WHERE status = 'READ ONLY' - 查最近一次全备包含哪些数据文件:
SELECT file#, bs_key FROM v$backup_datafile WHERE bs_key = (SELECT MAX(bs_key) FROM v$backup_set WHERE backup_type = 'D') - 对照
dba_data_files中对应表空间的file_id是否出现在结果里
如果没出现,说明确实跳过了;如果出现了,说明要么没加 SKIP READONLY,要么表空间状态不满足条件。
真正复杂的地方在于:RMAN 对只读表空间的处理是“状态驱动 + SCN 驱动”双校验,任何一个环节偏差,行为就和预期不一致。运维时得同时盯住数据库字典、控制文件快照、备份命令写法三处,缺一不可。











