Oracle Redo日志与Undo回滚段损坏恢复实战

Oracle Redo日志与Undo回滚段损坏恢复实战

没有RMAN备份的情况下,分别针对Redo日志损坏和Undo回滚段损坏的恢复方法。


场景一:Redo日志损坏恢复

数据库redo日志损坏,无法打开,没有备份。

恢复步骤

1. 设置隐藏参数允许损坏恢复
sql 复制代码
alter system set "_allow_resetlogs_corruption"=true scope=spfile;
alter system set "_allow_terminal_recovery_corruption"=true scope=spfile;

两个参数必须同时设置。第一个允许在resetlogs时容忍数据文件中的不一致数据,第二个允许终端恢复时容忍损坏。

2. 关闭数据库
复制代码
shutdown immediate;

如果immediate关不了,用shutdown abort

3. 启动到mount状态
复制代码
startup mount;
4. 使用备份控制文件恢复
sql 复制代码
recover database using backup controlfile until cancel;

提示输入日志文件时输入cancel------因为日志文件已经损坏了,无法应用。

5. 清理损坏的日志文件组
sql 复制代码
alter database clear logfile group <group_number>;

把损坏的redo日志组清理掉。<group_number>替换为实际的组号,可以通过select * from v$log;查看。

6. 用resetlogs方式打开数据库
sql 复制代码
alter database open resetlogs;

这是关键一步。resetlogs会重置日志序列号,相当于给数据库一个新的开始。

7. 切换日志
sql 复制代码
alter system switch logfile;

打开后立刻切换一次日志,确保新的redo日志正常工作。

8. 重置隐藏参数为false
sql 复制代码
alter system set "_allow_resetlogs_corruption"=false scope=spfile;
alter system set "_allow_terminal_recovery_corruption"=false scope=spfile;

恢复完成后必须把参数改回false,否则数据库长期运行在容忍损坏的状态下,后续问题会被掩盖。

9. 重启数据库
复制代码
shutdown immediate;
startup;

重启确认参数生效,数据库正常运行。

Redo恢复流程图

复制代码
设置 _allow_resetlogs_corruption=true
    ↓
关闭数据库
    ↓
startup mount
    ↓
recover database using backup controlfile until cancel → cancel
    ↓
alter database clear logfile group <n>
    ↓
alter database open resetlogs
    ↓
alter system switch logfile
    ↓
设置 _allow_resetlogs_corruption=false
    ↓
重启数据库

场景二:Undo回滚段损坏修复

数据库undo表空间损坏,同时可能有其他无关表空间也损坏。

修复步骤

1. 启动到mount状态
sql 复制代码
startup mount;
2. 从spfile创建pfile
sql 复制代码
create pfile from spfile;

pfile会生成在$ORACLE_HOME/dbs/目录下,文件名格式为init<SID>.ora

3. 关闭数据库
sql 复制代码
shutdown immediate;
4. 修改pfile文件

编辑$ORACLE_HOME/dbs/init<SID>.ora,修改以下两个参数:

复制代码
undo_management=MANUAL
undo_tablespace=SYSTEM

关键:把undo管理模式从AUTO改为MANUAL,把undo表空间从损坏的用户undo表空间改为系统表空间SYSTEM。这样Oracle启动时就不会去读损坏的undo表空间。

5. 用修改后的pfile启动到mount
sql 复制代码
startup mount pfile=$ORACLE_HOME/dbs/init<SID>.ora;
6. 查看数据文件列表
sql 复制代码
select file#, name from v$datafile;

记录所有数据文件的编号和路径。

7. 尝试打开数据库
sql 复制代码
alter database open;

如果提示某个数据文件需要恢复(那是损坏的表空间对应的文件),执行下一步。

8. 将损坏的数据文件offline并drop
sql 复制代码
alter database datafile <文件号> offline drop;

把损坏的表空间对应的数据文件offline掉,然后重新执行步骤7:

sql 复制代码
alter database open;

如果有多个损坏的文件,逐个offline drop后再open。

Undo恢复流程图

复制代码
startup mount
    ↓
create pfile from spfile
    ↓
shutdown immediate
    ↓
修改pfile: undo_management=MANUAL, undo_tablespace=SYSTEM
    ↓
startup mount pfile=...
    ↓
select file#, name from v$datafile (记录文件号)
    ↓
alter database open
    ↓
如果报错 → alter database datafile <n> offline drop → 重新open
    ↓
数据库打开成功

Undo恢复后要做的事

  1. 创建新的undo表空间

    sql 复制代码
    create undo tablespace undotbs2 datafile '/path/to/undotbs2.dbf' size 500M;
  2. 修改spfile指向新的undo表空间

    sql 复制代码
    alter system set undo_tablespace=undotbs2 scope=spfile;
    alter system set undo_management=AUTO scope=spfile;
  3. 重启数据库,确认使用新的undo表空间

  4. 删除旧的损坏的undo表空间(如果还能删的话)


注意事项

  1. 这是最后手段,有备份就不要用这些方法
  2. resetlogs后之前的备份全部失效,必须重新做全库备份
  3. 隐藏参数以_开头,Oracle不公开支持,生产环境慎用
  4. open resetlogs后建议立刻导出数据,重建数据库更安全
相关推荐
qxwlcsdn1 小时前
mysql在事务中执行DDL的后果_MySQL 8.0之前的限制
jvm·数据库·python
難釋懷2 小时前
Redis通信协议-基于Socket自定义Redis的客户端
数据库·redis·缓存
环流_2 小时前
redis:AOF
数据库·redis·spring
2401_884454152 小时前
如何防止SQL触发器导致性能下降_通过精简触发器逻辑
jvm·数据库·python
m0_596749092 小时前
Golang如何做Clean Architecture_Golang整洁架构教程【详解】
jvm·数据库·python
半夜修仙2 小时前
Redis入门
数据库·redis·缓存
KaMeidebaby2 小时前
卡梅德生物技术快报|单 B 细胞抗体筛选服务:技术架构、流程实现与数据验证
前端·数据库·其他·百度·新浪微博
2401_867623982 小时前
如何管理应用锁_DBMS_LOCK申请自定义锁控制并发逻辑
jvm·数据库·python
yzs872 小时前
SQL Sever Pragmatic Bitmap过滤技术解析
数据库·sql