RMAN实战16:ORACLE数据库的不完全恢复和闪回

时间:2022-11-26 12:30:18

不完全恢复指的是无法恢复所有已经提交的事务,无法对数据库应用所有的重做日志。通常有两种情景:1.必须的重做日志丢失或者损坏 2.有意将数据库会滚到过去的某个时间点。有两种方式组成:恢复数据+恢复已经提交的事务。可采用的手段有两种:RMAN(restore database until)和FLASHBACK DATABASE。

RESTORE DATABASE UNTIL

可以根据下列标示恢复到过去的时间点:
1. 时间
2. SCN
3. 日志序列号
4. 恢复点

UNTIL的作用:加入这个命令让RMAN从最新的备份集合镜像副本中获取所有数据文件,通过UNTIL RMAN可以确定哪个备份集中含有执行恢复操作的所需要的数据文件。
数是据文件的信息在v datafileheaderv datafile视图总可以查大,下面的这个sql可以插看数据文件的头部SCN和每个数据文件的状态,其中fuzzy列表示的是由一个或者多个数据块的SCN大于或者等于数据文件头部的检查点SCN,如果为YES表示当恢复的时候需要进行介质恢复操作。

sys@CYANG> select file#, status, fuzzy,
2 error, checkpoint_change#,
3 to_char(checkpoint_time,'dd-mon-rrrr hh24:mi:ss') as checkpoint_time
4 from v$datafile_header;


FILE# STATUS FUZ ERROR CHECKPOINT_CHANGE# CHECKPOINT_TIME
---------- ------- --- ----------- ------------------ -------------------------
1 ONLINE YES 4840160 28-12月-2015 18:52:35
2 ONLINE NO 2453693 02-9月 -2015 00:18:43
3 ONLINE YES 4840160 28-12月-2015 18:52:35
4 ONLINE NO 2453693 02-9月 -2015 00:18:43
5 ONLINE YES 4840160 28-12月-2015 18:52:35
6 ONLINE YES 4840160 28-12月-2015 18:52:35
7 ONLINE NO 4622783 23-12月-2015 20:08:42
8 ONLINE NO 4622783 23-12月-2015 20:08:42
9 ONLINE NO 4622783 23-12月-2015 20:08:42
10 ONLINE NO 4622783 23-12月-2015 20:08:42
12 ONLINE YES 4840160 28-12月-2015 18:52:35

已选择 11 行。

sys@CYANG>

执行不完全恢复需要满足的条件

  1. 数据库在归档模式下
  2. 拥有数据库文件的良好备份
  3. 拥有将数据库恢复到指定时间点所需的所有重做日志
  4. 处于mount模式

在执行恢复过程中,RMAN先应用所有可用的增量备份,然后应用存储在磁盘上的所有归档重做日志文件,如果这些归档重做日志文件没有储存在磁盘上,RMAN就会重试从备份集获取它们。

基于时间得恢复操作

$ rman target /
RMAN> startup mount;
RMAN> restore database until time
"to_date('15-jan-2013 12:20:00', 'dd-mon-rrrr hh24:mi:ss')";
RMAN> recover database until time
"to_date('15-jan-2013 12:20:00', 'dd-mon-rrrr hh24:mi:ss')";
RMAN> alter database open resetlogs;

基于日志序列号的恢复操作

RMAN-06053: unable to perform media recovery because of missing log
RMAN-06025: no backup of archived log for thread 1 with sequence 19...
--如果遇到了如上报错则需要进行序列恢复
$ rman target /
RMAN> startup mount;
RMAN> restore database until sequence 19;
RMAN> recover database until sequence 19;
RMAN> alter database open resetlogs;

基于SCN的恢复操作

如果知道具体的SCN可以进行SCN的恢复,可以通过以下方式获取SCN

  1. Logminer 确定ddl和dml命令的SCN
  2. 告警日志
  3. 跟踪文件
  4. v logv log_history、v$archive_log 视图的FRIST_CHANGE#列

确定了SCN后用如下命令恢复,注意这里恢复的都是小于某个SCN的值,其他的恢复方式也是。

$ rman target /
RMAN> startup mount;
RMAN> restore database until scn 95019865425;
RMAN> recover database until scn 95019865425;
RMAN> alter database open resetlogs;

基于还原点的恢复

可以创建于类似快照的的标志,将数据库恢复到某个快照时刻,也叫作还原点恢复,分为两种:标准和担保。二者的差异是担保还原点不会从控制文件中自动清除,但是可以手动删除。

其实还原点恢复也是基于SCN的恢复,就是在还原点处标记一个SCN。以上基于日志序列、时间得恢复本质上都是基于SCN的恢复,SCN是数据专用的时间标识。

创建一个还原点

--创建一个还原点
SQL> create restore point MY_RP;
--查看数据库当期的SCN
SQL> select current_scn from v$database;
--查看还原点信息
SQL> select name, scn from v$restore_point;

进行还原点恢复

$ rman target /
RMAN> startup mount;
RMAN> restore database until restore point MY_RP;
RMAN> recover database until restore point MY_RP;
RMAN> alter database open resetlogs;

12C新功能:基于表的恢复

从ORACLE 12C 开始,有了通过rman备份恢复某个表的功能,表级别恢复使用了临时辅助实例和数据泵。

--创建临时实例使用的文件存放的目录
$ mkdir /tmp/oracle
--创建数据泵存储数据文件用到的目录
$ mkdir /tmp/recover

--进行恢复
recover table mv_maint.inv
until scn 4689805
auxiliary destination '/tmp/oracle'
datapump destination '/tmp/recover';

恢复完毕后刚才创建的两个目录下产生的文件会被自动删除。

闪回功能

数据库的闪回功能从10G开始配置,能进行库级别的闪回也能进行表级别的闪回。

恢复已经drop的表

从10G开始配置了闪回功能,使用闪回表功能可以不需要实现FRA,数据库闪回也不是必须的。

--确认参数开启
SQL> show parameter recyclebin
--drop
SQL> drop table inv;

--查看回收站
SQL> show recyclebin;
OBJECT_NAME ORIGINAL_NAM TYPE
----------------------------------- ------------ -------------------------
BIN$0zIqhEFjcprgQ4TQTwq2uA==$0 INV_PK INDEX
BIN$0zIqhEFkcprgQ4TQTwq2uA==$0 INV_TRIG TRIGGER
BIN$0zIqhEFlcprgQ4TQTwq2uA==$0 INV TABLE
--用下面的这视图也可看回收站的东东
SQL>select object_name, original_name, type from recyclebin;
--进行表恢复
SQL> flashback table inv to before drop;
--这样恢复索引1
SQL> select index_name from user_indexes where table_name='INV';
INDEX_NAME
-------------------------------------------------
BIN$0zIqhEFjcprgQ4TQTwq2uA==$0
--这样恢复索引2
SQL> alter index "BIN$0zIqhEFjcprgQ4TQTwq2uA==$0" rename to inv_pk;
--恢复到别的名字
SQL> flashback table inv to before drop rename to inv_bef;

将表恢复到过去的时间点

下面做个不成功的演示来证明,在某些高级别的用户下(例如sys)是不支持闪回的,可以自己创建一个用户演示下,不出意外应该木问题的。

sys@CYANG> create table test11 (id number,name varchar(10));

表已创建。

sys@CYANG> insert into test11 values(1,'aa');

已创建 1 行。

sys@CYANG> insert into test11 values(2,'bb');

已创建 1 行。

sys@CYANG> insert into test11 values(3,'cc');

已创建 1 行。

sys@CYANG> commit
2 ;


提交完成。

sys@CYANG> select * from test11;

ID NAME
---------- ----------
1 aa
2 bb
3 cc

sys@CYANG> select current_scn from v$database;

CURRENT_SCN
-----------
4849456

sys@CYANG> alter table test11 enable row movement;

表已更改。

sys@CYANG> select current_scn from v$database;

CURRENT_SCN
-----------
4849484



sys@CYANG> insert into test11 values(4,'dd');

已创建 1 行。

sys@CYANG> commit;

提交完成。

sys@CYANG>


sys@CYANG> select * from test11;

ID NAME
---------- ----------
1 aa
2 bb
3 cc
4 dd

sys@CYANG> flashback table test11 to scn 4849456
2 ;
flashback table test11 to scn 4849456
*
第 1 行出现错误:
ORA-08185: 用户 SYS 不支持闪回


sys@CYANG>

将表闪回到时间戳

SQL> alter table inv enable row movement;
SQL> flashback table inv to timestamp(sysdate-1/96) ;
SQL> flashback table inv to timestamp
to_timestamp('14-jan-13 12:07:33','dd-mon-yy hh24:mi:ss');

将表闪回到还原点

SQL> create restore point point_a;
--如果没有针对此表启用行迁移功能则启用
SQL> alter table inv enable row movement;
SQL> flashback table inv to restore point point_a;

闪回数据库

条件:
1. 闪回数据库必须使用FRA
2. 启用归档
3. 启用闪回数据库功能

例子演示:

sys@CYANG> archive log list;
数据库日志模式 存档模式
自动存档 启用
存档终点 USE_DB_RECOVERY_FILE_DEST
最早的联机日志序列 6
下一个存档日志序列 8
当前日志序列 8
sys@CYANG> show parameter db_recovery

NAME TYPE VALUE
------------------------------------ ----------- ------------------------------
db_recovery_file_dest string C:\app\oracle\fast_recovery_ar
ea
db_recovery_file_dest_size big integer 12G

--开启闪回
sys@CYANG> alter database flashback on;


数据库已更改。

--查看下恢复时间,以min为单位
sys@CYANG> show parameter db_flash

NAME TYPE VALUE
------------------------------------ ----------- ------------------------------
db_flash_cache_file string
db_flash_cache_size big integer 0
db_flashback_retention_target integer 1440
#看下闪回日志
sys@CYANG> select name, log#, thread#, sequence#, bytes from v$flashback_database_logfile;


NAME
----------------------------------------------------------------------------------------------------
LOG# THREAD# SEQUENCE# BYTES
---------- ---------- ---------- ----------
C:\APP\ORACLE\FAST_RECOVERY_AREA\CYANG\FLASHBACK\O1_MF_C82D8M69_.FLB
1 1 1 52428800

C:\APP\ORACLE\FAST_RECOVERY_AREA\CYANG\FLASHBACK\O1_MF_C82D8OT3_.FLB
2 1 1 52428800

--看可以恢复的SCN范围
sys@CYANG> select
2 oldest_flashback_scn
3 ,to_char(oldest_flashback_time,'dd-mon-yy hh24:mi:ss')
4 from v$flashback_database_log;


OLDEST_FLASHBACK_SCN TO_CHAR(OLDEST_FLASHBAC
-------------------- -----------------------
4849843 28-12月-15 20:54:43
-- 创建还原点
sys@CYANG> create restore point flash_1;

还原点已创建。

--演示下闪回
sys@CYANG> shutdown immediate;
数据库已经关闭。
已经卸载数据库。
ORACLE 例程已经关闭。
sys@CYANG> startup
ORACLE 例程已经启动。

Total System Global Area 1560281088 bytes
Fixed Size 3046032 bytes
Variable Size 939525488 bytes
Database Buffers 603979776 bytes
Redo Buffers 13729792 bytes
数据库装载完毕。
数据库已经打开。
-- 在闪回的时候必须处于mont状态
sys@CYANG> flashback database to restore point flash_1;
flashback database to restore point flash_1
*
第 1 行出现错误:
ORA-38757: 要闪回数据库, 数据库必须已装载但不能打开。


sys@CYANG> shutdown abort
ORACLE 例程已经关闭。
sys@CYANG> startup mount
ORACLE 例程已经启动。

Total System Global Area 1560281088 bytes
Fixed Size 3046032 bytes
Variable Size 939525488 bytes
Database Buffers 603979776 bytes
Redo Buffers 13729792 bytes
数据库装载完毕。
sys@CYANG> flashback database to restore point flash_1;

闪回完成。

sys@CYANG> alter database open resetlogs;

数据库已更改。
--关闭闪回
sys@CYANG> alter database flashback off;

数据库已更改。

sys@CYANG>