必须先执行restore database还原出目标时间点前的数据文件,再用recover database until time应用日志,最后open resetlogs;单独执行recover会因数据文件过旧而报ora-01190或ora-01113错误。
不能只用 recover database until time,必须配合 restore database 和 set until time 三者联动,否则必然报 ora-01190 或 ora-01113。
为什么单独 recover database until time 会失败
RMAN 的 RECOVER DATABASE UNTIL TIME 不是“从当前状态往前滚”,而是“在已有合适数据文件基础上应用日志”。Oracle 11g 要求:还原出的数据文件头 checkpoint_time 必须 ≤ 目标时间点对应的 SCN;否则 RMAN 拒绝应用日志。你手头的备份通常比目标时间早很多,数据文件太旧,直接 recover 就会触发校验失败。
常见错误现象:
- 执行
recover database until time '2026-05-14 10:30:00'后报ORA-01190: control file or data file is from before the last RESETLOGS -
v$datafile中checkpoint_time明显早于目标时间,但没做 restore - 数据库处于 MOUNT 状态,
RECOVER却提示 “no backup of datafile found” —— 因为 RMAN 默认找最新备份,而非适配时间点的备份
set until time 必须放在 run 块最开头
SET UNTIL TIME 是上下文标记,不是独立命令。它只对后续所有 RESTORE 和 RECOVER 生效,且必须在 RESTORE 之前设置。写错位置等于没设。
容易踩的坑:
- 把
set until time放在restore database后面 → RMAN 忽略,按最新备份还原,recover必然失败 - 时间格式不匹配:
'2026-05-14 10:30'缺少秒,或用单引号包裹双引号 → 报RMAN-03002: failure of set command - 没设
NLS_DATE_FORMAT环境变量,又在 SQL*Plus 里查过sysdate→ RMAN 解析失败(RMAN 不读取会话级 NLS 设置) - 目标时间点超出归档日志覆盖范围:比如备份中数据文件最低 SCN 是 1000000,目标时间对应 SCN 是 999999,但中间缺归档 →
RECOVER卡住或报 “archivelog not found”
正确执行顺序与最小可行示例
三步不可省、不可调序:mount → set until → restore → recover → open resetlogs。
典型写法(注意引号和格式):
run {
startup force mount;
set until time "to_date('2026-05-14 10:30:00','yyyy-mm-dd hh24:mi:ss')";
restore database;
recover database;
alter database open resetlogs;
}
关键说明:
-
startup force mount确保干净进入 MOUNT,避免残留实例干扰 -
to_date(...)写法比纯字符串更可靠,尤其跨时区或 NLS 不一致时 - 不用手动指定备份集路径 —— RMAN 自动根据
SET UNTIL选最接近且满足条件的备份 -
open resetlogs不可省:不完全恢复后联机日志已失效,必须重置日志序列号
恢复前必须确认的三件事
跳过任何一项都可能导致恢复中断或数据不一致:
- 归档日志是否完整?用
list archivelog all检查目标时间点前后序列是否连续,特别留意DELETED状态的归档 - 控制文件是否可用?如果用备份控制文件恢复,需先
restore controlfile,再startup mount,否则set until可能解析失败 - 目标时间点是否落在备份 + 归档可覆盖范围内?查
v$database的RESETLOGS_TIME和v$backup_datafile的COMPLETION_TIME,确保目标时间早于最新备份完成时间、晚于最老归档起始 SCN
resetlogs 后的数据库是一个新 incarnation,旧备份无法再用于后续恢复 —— 这一点常被忽略,但直接影响灾备链路有效性。











