ITPub博客

首页 > Linux操作系统 > Linux操作系统 > Flashback实验

Flashback实验

原创 Linux操作系统 作者:dnd_lishangyun 时间:2010-12-16 09:23:47 0 删除 编辑

 Flashback实验

今天做这个实验,是有关于flashback的。首先看一下到底在什么情况下使用,oracle数据库中发生了逻辑损坏时可以使用闪回技术。什么是逻辑损坏?说白了就是你的数据文件还在,如果数据文件损坏就属于物理损坏。

那么逻辑损坏又有哪些?如果不小心删除了表,没关系,可以通过闪回从回收站找回来。如果你对表做了误操作,删除了数据,错误的更新了数据也可以闪回。

但这里强调一下如果你不小心删除了表空间,是没有办法通过flashback恢复的,只用通过rman或用户自定义备份通过原来(即表空间删除之前备份的控制文件)控制文件来恢复。下面开始试验,主要从三个级别来,闪回查询,闪回表,闪回数据库。

闪回查询

使用flashback有许多先觉条件,首先你得启用自动撤销表空间,然后每个等级的闪回也分别由不同的条件。

自动撤销表空间(Automatic Undo Managerment),这个在10g上都是默认启动的,可以看一下

SQL> show parameter undo

 

NAME                                 TYPE        VALUE

------------------------------------ ----------- ------------------------------

undo_management                      string      AUTO

undo_retention                       integer     900

undo_tablespace                      string      UNDOTBS1

我这里可以看到有三个参数undo_management auto 表明是自动管理,也可以改成手动manual,淡然如果你不清楚如何管理还是不要乱改的好。

undo_tablespace UNDOTBS1这个是系统默认的undo表空间,你也可以手工建一个create undo tablespace undo1 datafile ‘/opt/oracle/ora10g/undo1.dbf’ size 50m;如果udno表空间过小,肯定会影响到flashback,同时可能会触发ora-1555.

那么最后一个参数undo_retention这个是干什么的呢? 就是看是否retention guarantee,如果有,15分钟内一个transaction被committed后不会被覆盖。如果没有guarantee(既NOGUARANTEE),那么undo如果有空间就不会被覆盖,如果没有就会立即被覆盖。怎么查看是否guarantee?

 

 

 

 

SQL> select TABLESPACE_NAME,BLOCK_SIZE, RETENTION from dba_tablespaces where TABLESPACE_NAME='UNDOTBS1';

 

TABLESPACE_NAME                BLOCK_SIZE RETENTION

------------------------------ ---------- -----------

UNDOTBS1                             8192 NOGUARANTEE

1.         基于时间闪回

SQL> select * from students;

 

    SNO SNAME    SEX       AGE BPLACE

------- -------- -------- ---- --------------------

  95032 赵新3    男         20 新疆

  95034 赵新4    男         20 新疆

  95035 赵新5    男         20 新疆

  95036 赵新6    男         20 新疆

  95037 赵新7    男         20 新疆

  95038 赵新8    男         20 新疆

  95039 赵新9    男         20 新疆

  95040 赵新10   男         20 新疆

  95043 lily2    女         20 新疆

  95044 lily3    女         20 新疆

  95045 lily4    女         20 新疆

  95046 lily5    女         20 新疆

  95047 lily6    女         20 新疆

  95048 lily8    女         20 新疆

  95049 lily9    女         20 新疆

  95050 lily10   女         20 新疆

  95029 赵新     女         38 新疆

  95031 赵新2    男         20 新疆

 

18 rows selected

这是students表,我们把其中的男同学删掉

SQL> delete from students where sex='男' ;

 

9 rows deleted

 

SQL> commit;

 

Commit complete

再查询一下

SQL> select * from students;

 

    SNO SNAME    SEX       AGE BPLACE

------- -------- -------- ---- --------------------

  95043 lily2    女         20 新疆

  95044 lily3    女         20 新疆

  95045 lily4    女         20 新疆

  95046 lily5    女         20 新疆

  95047 lily6    女         20 新疆

  95048 lily8    女         20 新疆

  95049 lily9    女         20 新疆

  95050 lily10   女         20 新疆

  95029 赵新     女         38 新疆

 

9 rows selected

 

SQL>

看到男同学都被删除了,大约过十分钟左右,我们使用闪回查询

SQL> select * from students  as of timestamp sysdate-10/1440;

 

    SNO SNAME    SEX       AGE BPLACE

------- -------- -------- ---- --------------------

  95032 赵新3    男         20 新疆

  95034 赵新4    男         20 新疆

  95035 赵新5    男         20 新疆

  95036 赵新6    男         20 新疆

  95037 赵新7    男         20 新疆

  95038 赵新8    男         20 新疆

  95039 赵新9    男         20 新疆

  95040 赵新10   男         20 新疆

  95043 lily2    女         20 新疆

  95044 lily3    女         20 新疆

  95045 lily4    女         20 新疆

  95046 lily5    女         20 新疆

  95047 lily6    女         20 新疆

  95048 lily8    女         20 新疆

  95049 lily9    女         20 新疆

  95050 lily10   女         20 新疆

  95029 赵新     女         38 新疆

  95031 赵新2    男         20 新疆

 

18 rows selected

 

SQL>

好,这是再删除男同学之前的表,我们再插入回students

SQL> insert into students  select * from students  as of timestamp sysdate-10/1440 where sex='男';

 

9 rows inserted

SQL> commit;

 

Commit complete

查询一下

SQL> select * from students;

 

    SNO SNAME    SEX       AGE BPLACE

------- -------- -------- ---- --------------------

  95043 lily2    女         20 新疆

  95044 lily3    女         20 新疆

  95045 lily4    女         20 新疆

  95046 lily5    女         20 新疆

  95047 lily6    女         20 新疆

  95048 lily8    女         20 新疆

  95049 lily9    女         20 新疆

  95050 lily10   女         20 新疆

  95029 赵新     女         38 新疆

  95032 赵新3    男         20 新疆

  95034 赵新4    男         20 新疆

  95035 赵新5    男         20 新疆

  95036 赵新6    男         20 新疆

  95037 赵新7    男         20 新疆

  95038 赵新8    男         20 新疆

  95039 赵新9    男         20 新疆

  95040 赵新10   男         20 新疆

  95031 赵新2    男         20 新疆

 

18 rows selected

表已回复

2.         基于SCN闪回

查询SCN,查询SCN据我所知有两种方法

SQL> select dbms_flashback.get_system_change_number from dual;

 

GET_SYSTEM_CHANGE_NUMBER

------------------------

                  697126

 

SQL>  select current_scn from v$database;

 

CURRENT_SCN

-----------

     697128

 

SQL>

这两种有什么区别,我也不知道,反正都可以查

还是刚才那个表,我们把女同学都删除,

 

SQL> delete from students where sex='女';

 

9 rows deleted

 

SQL> commit;

 

Commit complete

 

SQL> select * from students;

 

    SNO SNAME    SEX       AGE BPLACE

------- -------- -------- ---- --------------------

  95032 赵新3    男         20 新疆

  95034 赵新4    男         20 新疆

  95035 赵新5    男         20 新疆

  95036 赵新6    男         20 新疆

  95037 赵新7    男         20 新疆

  95038 赵新8    男         20 新疆

  95039 赵新9    男         20 新疆

  95040 赵新10   男         20 新疆

  95031 赵新2    男         20 新疆

 

9 rows selected

 

SQL>

使用scn恢复

SQL> select * from students as of scn 697128;

 

    SNO SNAME    SEX       AGE BPLACE

------- -------- -------- ---- --------------------

  95043 lily2    女         20 新疆

  95044 lily3    女         20 新疆

  95045 lily4    女         20 新疆

  95046 lily5    女         20 新疆

  95047 lily6    女         20 新疆

  95048 lily8    女         20 新疆

  95049 lily9    女         20 新疆

  95050 lily10   女         20 新疆

  95029 赵新     女         38 新疆

  95032 赵新3    男         20 新疆

  95034 赵新4    男         20 新疆

  95035 赵新5    男         20 新疆

  95036 赵新6    男         20 新疆

  95037 赵新7    男         20 新疆

  95038 赵新8    男         20 新疆

  95039 赵新9    男         20 新疆

  95040 赵新10   男         20 新疆

  95031 赵新2    男         20 新疆

 

18 rows selected

 

SQL>

SQL> insert into students  select * from students as of scn 697128 where sex='女';

 

9 rows inserted

SQL> commit;

 

Commit complete

已经恢复

 

其实scn就是oracle中的时间,只不过使用oracle使用scn作为数据库的时间基准

通过查询

SQL> select scn ,to_char(time_dp, 'yyyy-mm-dd hh24:mm:ss') from sys.smon_scn_time;

       SCN TO_CHAR(TIME_DP,'YYYY-MM-DDHH2

---------- ------------------------------

    689961 2010-12-01 17:12:56

    690457 2010-12-01 17:12:53

    690712 2010-12-01 17:12:57

    690924 2010-12-01 17:12:51

    693199 2010-12-01 17:12:01

    693413 2010-12-01 17:12:01

    693666 2010-12-01 17:12:52

    693724 2010-12-01 17:12:52

    694409 2010-12-01 17:12:46

    694658 2010-12-01 17:12:56

    694941 2010-12-01 17:12:59

    695095 2010-12-01 17:12:53

    695610 2010-12-01 17:12:57

    695904 2010-12-01 18:12:51

    695986 2010-12-01 18:12:07

    696242 2010-12-01 18:12:12

    696945 2010-12-01 18:12:13

    697157 2010-12-01 18:12:17

    697351 2010-12-01 18:12:11

    697825 2010-12-01 18:12:17

 

3.         版本查询

VERSIONS BETWEEN 是这样一种查询,当你表进行过多次修改,连你自己也不清楚改了几次,你需要把你做了什么操作都显示出来,以来恢复。

当前scn

SQL> select dbms_flashback.get_system_change_number from dual;

 

GET_SYSTEM_CHANGE_NUMBER

------------------------

                  718751

先删两个男同学,

delete from students where sno=95032 or sno=95044;scn= 718796

再删两个女同学

delete from students where sno=95043 or sno=95045;scn= 718874

删掉所有男同学

delete from students where sex='男';scn= 718948

删掉所有女同学

delete from students where sex='女';scn= 718967

 

查看版本结果

SQL> select SNO,SNAME,SEX,AGE,BPLACE,versions_startscn,versions_endscn,versions_operation

  2  from students versions between scn 718751 and 718967 order by 1;

 

    SNO SNAME    SEX       AGE BPLACE               VERSIONS_STARTSCN VERSIONS_ENDSCN VERSIONS_OPERATION

------- -------- -------- ---- -------------------- ----------------- --------------- ------------------

  95029 赵新     男         20 新疆                                            718928

  95029 赵新     男         20 新疆                            718928                 D

  95030 赵新1    男         20 新疆                            718928                 D

  95030 赵新1    男         20 新疆                                            718928

  95031 赵新2    男         20 新疆                            718928                 D

  95031 赵新2    男         20 新疆                                            718928

  95032 赵新3    男         20 新疆                                            718790

  95032 赵新3    男         20 新疆                            718790                 D

  95034 赵新4    男         20 新疆                                            718928

  95034 赵新4    男         20 新疆                            718928                 D

  95035 赵新5    男         20 新疆                            718928                 D

  95035 赵新5    男         20 新疆                                            718928

  95036 赵新6    男         20 新疆                                            718928

  95036 赵新6    男         20 新疆                            718928                 D

  95037 赵新7    男         20 新疆                            718928                 D

  95037 赵新7    男         20 新疆                                            718928

  95038 赵新8    男         20 新疆                                            718928

  95038 赵新8    男         20 新疆                            718928                 D

  95039 赵新9    男         20 新疆                            718928                 D

  95039 赵新9    男         20 新疆                                            718928

 

    SNO SNAME    SEX       AGE BPLACE               VERSIONS_STARTSCN VERSIONS_ENDSCN VERSIONS_OPERATION

------- -------- -------- ---- -------------------- ----------------- --------------- ------------------

  95040 赵新10   男         20 新疆                            718928                 D

  95040 赵新10   男         20 新疆                                            718928

  95041 lily     女         20 新疆                                            718964

  95041 lily     女         20 新疆                            718964                 D

  95042 lily1    女         20 新疆                            718964                 D

  95042 lily1    女         20 新疆                                            718964

  95043 lily2    女         20 新疆                                            718852

  95043 lily2    女         20 新疆                            718852                 D

  95044 lily3    女         20 新疆                                            718790

  95044 lily3    女         20 新疆                            718790                 D

  95045 lily4    女         20 新疆                            718852                 D

  95045 lily4    女         20 新疆                                            718852

  95046 lily5    女         20 新疆                                            718964

  95046 lily5    女         20 新疆                            718964                 D

  95047 lily6    女         20 新疆                            718964                 D

  95047 lily6    女         20 新疆                                            718964

  95048 lily8    女         20 新疆                            718964                 D

  95048 lily8    女         20 新疆                                            718964

  95049 lily9    女         20 新疆                            718964                 D

  95049 lily9    女         20 新疆                                            718964

  95050 lily10   女         20 新疆                            718964                 D

 

    SNO SNAME    SEX       AGE BPLACE               VERSIONS_STARTSCN VERSIONS_ENDSCN VERSIONS_OPERATION

------- -------- -------- ---- -------------------- ----------------- --------------- ------------------

  95050 lily10   女         20 新疆                                            718964

 

42 rows selected

 

事务查询(Transaction query)

Flashback的事务查询时通过查询flashback_transaction_query视图来实现的。通过查询该视图能够获得一些事务执行时的信息,甚至包括undo语句。

查看当前scn:

SQL> select dbms_flashback.get_system_change_number from dual;

 

GET_SYSTEM_CHANGE_NUMBER

------------------------

                  723625

首先删除一条记录:

SQL> delete from students where sno=95030;

 

1 row deleted

使用Transaction query

select xid,commit_scn,commit_timestamp,operation,undo_sql

from flashback_transaction_query q where q.xid in(

select versions_xid from lsy.students versions between scn 723625 and 725223);

但是报了一个错:

ORA-30052: invalid lower limit snapshot expression

百度了一下,发现是有关于undo_retention=900s的原因,我在15分钟内并没有做过大规模dml操作,也就是应该把undo数据覆盖掉。可能是我两次scn的时间超过了15分钟。

这里我有一个疑问,用select * from students as of scn 723625;可以查询到该scn表的数据,但是使用version between scn 723625 and 725223 就会报:

ORA-30052: invalid lower limit snapshot expression

如果说被覆盖的话查询scn723625是查询不到的。

 

我们继续在做一遍删除操作,并记录下scn,重新:

SQL> select xid,commit_scn,commit_timestamp,operation,undo_sql

  2  from flashback_transaction_query q where q.xid in(

  3  select versions_xid from lsy.students versions between scn 726320 and 726358);

 

XID              COMMIT_SCN COMMIT_TIMESTAMP OPERATION                        UNDO_SQL

---------------- ---------- ---------------- -------------------------------- --------------------------------------------------------------------------------

09000700F2010000     726340 2010-12-2 0:35:2 DELETE                           insert into "LSY"."STUDENTS"("SNO","SNAME","SEX","AGE","BPLACE") values ('95031'

09000700F2010000     726340 2010-12-2 0:35:2 BEGIN                           

 

大家可以看到undo数据了 。

这还是flashback_transaction_query表的数据,最早的scn可以追寻到718291,但是却报错,那么肯定是这句select versions_xid from lsy.students versions between scn 723625 and 725223。究竟为什么还得找个大神解释一下。

 

 

 

闪回表

前面说了一下闪回查询,下面说一下闪回表。这个粒度要大于闪回查询。闪回查询都是查询到表先前的数据,再把误操作的数据改回去。

闪回表可以从两个地方恢复,一个是回收站(recycle bin),另一个就是从undo数据中。

Recycle Bin

首先drop掉student这个表

SQL> drop table students;

Table dropped

然后恢复

SQL> flashback table students to before drop;

 

Done

 

SQL> select * from students;

 

    SNO SNAME    SEX       AGE BPLACE

------- -------- -------- ---- --------------------

  95032 赵新3    男         20 新疆

  95029 赵新     男         20 新疆

  95034 赵新4    男         20 新疆

  95035 赵新5    男         20 新疆

  95036 赵新6    男         20 新疆

  95037 赵新7    男         20 新疆

  95038 赵新8    男         20 新疆

  95039 赵新9    男         20 新疆

  95040 赵新10   男         20 新疆

  95041 lily     女         20 新疆

  95042 lily1    女         20 新疆

  95043 lily2    女         20 新疆

  95044 lily3    女         20 新疆

  95045 lily4    女         20 新疆

  95046 lily5    女         20 新疆

  95047 lily6    女         20 新疆

  95048 lily8    女         20 新疆

  95049 lily9    女         20 新疆

  95050 lily10   女         20 新疆

 

19 rows selected

很简单,这里多说两句,如果你想彻底删除表,连recycle bin 里都不放可以使用purge命令:

清除指定表:purge table ;
??
清除当前用户的回收站:
purge recyclebin;
??
清除所有用户的回收站:purge dba_recyclebin;

如果你已经建立要恢复的表,这时候是需要在后面加上rename to即可

flashback table students to before drop rename to stu1;

当然也可以查询recycle bin里面的内容

表恢复以后,recycle bin里的相关内容也随之消失,和windows回收站很相似。

UNDO恢复

查询当前scn

SQL> select dbms_flashback.get_system_change_number from dual;

 

GET_SYSTEM_CHANGE_NUMBER

------------------------

                  748700

这个也很简单 ,我们先删除表students中的内容

SQL> delete students;

 

19 rows deleted

 

SQL> commit;

 

Commit complete

 

SQL>

恢复表students

SQL> flashback table students to scn 748700;

 

flashback table students to scn 748700

 

ORA-08189: cannot flashback the table because row movement is not enabled

 

SQL>

哎呦报错了,row movement没有打开,这里补充一下要使用UNDO恢复表,必须要打开row movement。

我们先来打开row movement

SQL> alter table students enable row movement;

 

Table altered

下面再来恢复

SQL> flashback table students to scn 748700;

 

Done

好了恢复了,使用timestamp和scn是一个道理我就不重复了

数据库级闪回

如果你的数据文件没有损坏,同时你对你数据库的表了如指掌,那么使用闪回数据库还是很方便的。

当然使用数据库闪回也是有条件的

首先数据库必须启用了flashback database

数据库必须打开了flash recovery area

数据库必须在归档模式下

1.         检查数据库是否处于归档模式

SQL> archive log list;

Database log mode              Archive Mode

Automatic archival             Enabled

Archive destination            USE_DB_RECOVERY_FILE_DEST

Oldest online log sequence     11

Next log sequence to archive   13

Current log sequence           13

SQL>

2.         检出数据库是否启用了flashback database

       SQL> select flashback_on , force_logging from v$database;

 

FLASHBACK_ON       FORCE_LOGGING

------------------ -------------

NO                 NO

关闭的把他打开

SQL> alter database force logging;

 

Database altered

这个参数可以下数据库open的情况下打开

 

SQL> alter database flashback on;

 

alter database flashback on

 

ORA-38759: Database must be mounted by only one instance and not open.

 

SQL

这个就不可以了,必须在mount状态下打开

SQL> startup mount;

ORACLE instance started.

 

Total System Global Area  159383552 bytes

Fixed Size                  1218292 bytes

Variable Size             134220044 bytes

Database Buffers           20971520 bytes

Redo Buffers                2973696 bytes

Database mounted.

SQL> alter database flashback on;

 

Database altered.

 

SQL>

好了

再检查一下

SQL> select flashback_on , force_logging from v$database;

 

FLASHBACK_ON       FORCE_LOGGING

------------------ -------------

YES                YES

3.         检查数据库是否打开了flash recovery area

SQL> show parameter db_recovery_file;

 

NAME                                 TYPE        VALUE

------------------------------------ ----------- ------------------------------

db_recovery_file_dest                string      /opt/ora10g/flash_recovery_area

db_recovery_file_dest_size           big integer 1G
下面我们开始做闪回数据库的实验:

取得scn

SQL> select dbms_flashback.get_system_change_number from dual;

 

GET_SYSTEM_CHANGE_NUMBER

------------------------

                  751811

删除表students

SQL> drop table students;

 

Table dropped

必须把数据库改到mounted状态,才能闪回数据库

SQL> select status from v$instance;

 

STATUS

------------

MOUNTED

 

SQL>

闪回数据库

 

SQL> flashback database to scn 751811;

 

Flashback complete.

接着以resetlogs模式打开

 

SQL> alter database open resetlogs;

 

Database altered.

验证数据

SQL> select * from students;

 

    SNO SNAME    SEX       AGE BPLACE

------- -------- -------- ---- --------------------

  95032 赵新3    男         20 新疆

  95029 赵新     男         20 新疆

  95034 赵新4    男         20 新疆

  95035 赵新5    男         20 新疆

  95036 赵新6    男         20 新疆

  95037 赵新7    男         20 新疆

  95038 赵新8    男         20 新疆

  95039 赵新9    男         20 新疆

  95040 赵新10   男         20 新疆

  95041 lily     女         20 新疆

  95042 lily1    女         20 新疆

  95043 lily2    女         20 新疆

  95044 lily3    女         20 新疆

  95045 lily4    女         20 新疆

  95046 lily5    女         20 新疆

  95047 lily6    女         20 新疆

  95048 lily8    女         20 新疆

  95049 lily9    女         20 新疆

  95050 lily10   女         20 新疆

 

19 rows selected

 

SQL

数据恢复

 

最后再解释一下一个参数

SQL> show parameter flash

 

NAME                                 TYPE        VALUE

------------------------------------ ----------- ------------------------------

db_flashback_retention_target        integer     1440

这个参数是干什么的呢?是不是和undo_retention有点像

该参数用来控制 flashback log 数据保留的时间,或者说,你希望 flashback database 能够恢复的最早的时间点。默认值是 1440 ,单位是 minute ,即 24 小时,需要注意的是该参数虽然未直接指定 flash recovery area大小,但却受其制约,举个例子假如数据库每天有 10% 左右的数据变动的话,如果该初始化参数值设置为1440 ,则 flash recovery area 的大小至少要是当前数据库实际容量的 10% ,如果该初始化参数设置为 2880 ,则 flash recovery area 的 大小就至少是数据库所占容量的 20%。

                                                                                    2010-12-15 by饼干

 

 

来自 “ ITPUB博客 ” ,链接:https://blog.itpub.net/23493401/viewspace-681951/ ,如需转载,请注明出处,否则将追究法律责任。

下一篇: 没有了~
请登录后发表评论 登录
全部评论

注册时间:2010-03-11

  • 博文量
    13
  • 访问量
    21036