1、闪回查询之As of timestamp 2、闪回查询之As of scn
3、闪回查询之Versions between 4、闪回查询之Transaction query
5、闪回查询之制约因素
[@more@]此时表中id<5的记录均已被删除,假设过了一会儿你发现删除操作执行有误,仍需找回那些被误删的记录该怎么办呢?使用备份恢复?如果是在8i,恐怕是需要这样,自9i之后,使用flashback query的特性,我们可以很轻松的恢复记录(注意并不是任何情况下都可以恢复哟,后面会讲到制约flashback query的一些因素,我们这里举的都是理想条件下的例子),假设当前距离删除数据已经有2分钟左右的话:
SQL> select * from flashtable as of timestamp sysdate-2/1440;
返回的记录数则是删除前的数据,仍是49行记录
49 rows selected.
SQL> insert into flashtable select * from flashtable as of timestamp sysdate-2/1440;
as of timestamp|scn的语法是自9iR2后才开始提供支持,如果是9iR1版本,需要使用DBMS_FLASHBACK包来应用flashback query的特性。如上述示例中所表示的,as of timestamp的确非常易用,但是在某些情况下,我们建议使用as of scn的方式执行flashback query,比如需要对多个相互有主外键约束的表进行恢复时,如果使用as of timestamp的方式,可能会由于时间点不统一的缘故造成数据选择或插入失败,通过scn方式则能够确保记录的约束一致性。
或者:select * from fp_nsrjc as of timestamp (systimestamp-interval'10'hour);此语句也可以.
(2)、基于scn的方法
既然是基于scn的查询,我们首先就需要得到scn,这里我们通过dbms_flashback.get_system_change_number函数来获取当前的scn,之后再执行数据的修改操作。
SQL> select dbms_flashback.get_system_change_number from dual;
GET_SYSTEM_CHANGE_NUMBER
------------------------
904007
SQL> delete from flashtable where id>=40;
10 rows deleted.
SQL> select * from flashtable as of scn 904007;
SQL> insert into flashtable select * from flashtable as of scn 904007 where id not in (select id from flashtable);
10 rows created.
事实上,Oracle在内部都是使用scn,即使你指定的是as of timestamp,oracle也会将其转换成scn,系统时间标记与scn之间存在一张表,即SYS下的SMON_SCN_TIME
SQL> desc sys.smon_scn_time;
每隔5分钟,系统产生一次系统时间标记与scn的匹配并存入sys.smon_scn_time表,该表中记录了最近1440个系统时间标记与scn的匹配记录,由于该表只维护了最近的1440条记录,因此如果使用as of timestamp的方式则只能最近5天内的数据(假设系统是在持续不断运行并无中断或关机重启之类操作的话)。注意理解系统时间标记与scn的每5分钟匹配一次这句话,举个例子,比如scn:339988,339989分别匹配08-05-30 13:52:00和2008-13:57:00,则当你通过as of timestamp查询08-05-30 13:52:00或08-05-30 13:56:59这段时间点内的时间时,oracle都会将其匹配为scn:339988到undo表空间中查找,也就说在这个时间内,不管你指定的时间点是什么,查询返回的都将是08-05-30 13:52:00这个时刻的数据。
当然,具体的情况,我想你亲自执行一下select scn,to_char(time_dp,'yyyy-mm-dd hh24:mi:ss') from sys.smon_scn_time,会理解的更深刻一些。
(3)、versions beween
版本查询的用法并不比as of复杂,与其类似,你只需要在标准查询后面附加versions between timestamp[/scn] t1 and t2即可。记录在版本查询中可能会是一对多的关系,比如某些记录如果被修改过多次,并分别提交,那么你在查询的时候,如果修改的操作是在你指定的时间段(或scn),则记录每次修改的结果都会被选择出来,这比较有利于我们做数据的对比,比如看看数据究竟是怎么变化的。
VERSIONS_STARTSCN
VERSIONS_STARTTIME
该记录失效时的scn或时间,如果为空,说明记录当前时间在当前表内存在,或者已经被删除了,可以配合着VERSIONS_OPERATION列来看,如果VERSIONS_OPERATION列值为D,说明该列已被删除,如果该列为空,则说明记录在这段时间无操作
SQL> select dbms_flashback.get_system_change_number from dual;
GET_SYSTEM_CHANGE_NUMBER
------------------------
905676
SQL> update flashtable set id=id+100 where id<=5;
5 rows updated.
SQL> insert into flashtable values(101,'a');
1 row created.
SQL> select dbms_flashback.get_system_change_number from dual;
GET_SYSTEM_CHANGE_NUMBER
------------------------
905796
SQL> select id,name,versions_startscn,versions_endscn,versions_operation from flashtable versions between scn 905676 and 905796 order by 2;
根据这个结果返回我们首先来看id<5的记录,每个记录各有两个版本,一行的VERSIONS_VERSIONS_ENDSCN有值,记录了该版本失效时的scn。
另有5行id>100 and id<200的,从VERSIONS_OPERATION列可以看出操作是update,这是我们手工执行update set的结果
来自 “ ITPUB博客 ” ,链接:http://blog.itpub.net/25682487/viewspace-1048596/,如需转载,请注明出处,否则将追究法律责任。
转载于:http://blog.itpub.net/25682487/viewspace-1048596/