发布网友 发布时间:2022-04-23 09:48
共1个回答
热心网友 时间:2022-04-09 14:13
这部分的内容,其实早在10年年初就学习过,也记录了相关的笔记.但很多知识不用就慢慢被遗忘了.今天无意中听到同事在讨论问题:为什么删除了一个占用空间大的表后,表空间并没有释放呢?
职业的原因,自己在想Oracle Drop table的过程是怎么实现的,是不是要做个跟踪看下.后来想起在10g后,Oracle有了Flashback的功能,删除表的时候会先放在RecycleBin中,并不真正的物理删除,所以表空间dba_free_space是不是不会有变化?
今天重新翻了下之前的笔记,并做了试验,发现dba_free_space也是会体现变化的,这是不是哪个环节理解上有问题,还需要再测试下
目录:
1 Flashback Database 架构
2 Flashback Database
3 Flashback Drop
4 Flashback Query and Flashback Table
5 小结
#####################################################
1、 Flashback Database 架构
#####################################################
Flashback Database 整个架构包括一个进程Recover Writer(RVWR)后台进程,Flashback Database Log日志和Flash Recovery Area
一旦数据库启用了Flash Database, RVWR进程会启动,RVWR进程会向Flash Recovery Area内写入Flashback Database Log, 这些日志包括数据块的"前镜像"
#####################################################
2 、Flashback Database
#####################################################
1 启用Flashback Database
1.1 配置Flash Recovery Area
1)启用Flash Recovery Area
Alter system set db_recovery_file_dest_size=1G scope=both;
Alter system set db_recovery_file_dest='/u01/backup/fb' scope=both;
注意这个目录必须是Oracle:dba,属主
col name format a32 heading 'Parameter'
col value format a32 heading 'Setting'
select name, value from v$parameter where name like '%flash%' or name like '%recovery%' order by name;
2) 启用数据库Flashback功能
数据库必须处于归档模式
#重启数据库
startup mount(在Open下也可以打开)
#检查有没有开启Flashback功能
select name, current_scn, flashback_on from v$database;
#启动Flashback功能
alter database flashback on;
#确认启动
select name, current_scn, flashback_on from v$database;
#确认Flashback Log生成在/u01/backup/fb/目录下,该目录为OMF管理
oracle@Z810:/u01/backup/fb/MOUSE/flashback> ll /u01/backup/fb/MOUSE/flashback
total 8020
-rw-r----- 1 oracle dba 8200192 Aug 2 16:32 o1_mf_65f0nym9_.flb
# 设置db_flashback_retention_target参数
Alter system set db_flashback_retention_target=1440 scope=both;
单位为分钟
如果/u01/backup/fb/目录下的空间不够保存一天的回退数据怎么办呢?
Override;
#打开数据库
Alter database open;
2 Flashback Database
1) 确认能够恢复的时间点
SQL> desc v$flashback_database_log;
Name Null? Type
----------------------------------------- -------- ----------------------------
OLDEST_FLASHBACK_SCN NUMBER
OLDEST_FLASHBACK_TIME DATE
RETENTION_TARGET NUMBER
FLASHBACK_SIZE NUMBER
ESTIMATED_FLASHBACK_SIZE NUMBER
OLDEST_FLASHBACK_SCN: 数据库能回退的最早SCN
OLDEST_FLASHBACK_TIME: 数据库能回退的最早时间
RETENTION_TARGET:当前系统设置参数
FLASHBACK_SIZE: Current size (in bytes) of the flashback data 当前的Flashback Log空间
ESTIMATED_FLASHBACK_SIZE: 为了达到Retention_target定义的要求,预计需要多大的空间,这个值用于指导设置Flash Recovery Area大小
这个会改变
2) Flashback database
Flashback Database 实际上是对数据库的一个不完全恢复操作,因此需要关闭数据库,重启数据库到Mount状态;但与不完全恢复不同的是,它不需要执行restore操作。
flashback之前,先对数据库做个备份
#backup database;
#Shutdown immediate
#startup mount
#flashback database to timestamp to_timestamp('2010-08-02 17:10:04','yyyy-mm-dd hh24:mi:ss');
如何精确到找到恢复时间点呢?SCN_TO_TIMESTATMP()函数可以将SCN号转换成TimeStamp
如何找到某个操作的精确时间点,AUDIT?
#alter database open read only;
#select count(*) from xxx; 确认数据被找回
#shutdown immediate;
#Startup mount;
#alter database open resetlogs;
#backup database;
3 命令和视图
1) 检查是否启用了Flashback database 功能
Select flashback_on from v$database
2) v$flashback_database_log
这个视图用来描述Flashback log对Flash Recovery Area的占用情况
select * from v$flashback_database_log;
3) v$flashback_database_stat
这个视图用来对Flashback log的空间情况进行更细粒度的记录和估计
4) Flashback命令
这个命令既可以在SQL*Plus中使用,也可以在RMAN中使用,
Flashback [device type = <device type> ] database
to [before] scn = <scn>
to [before] sequence = <sequence> [ thread = <thread id> ]
to [before] time = '<data_string>'
Oracle允许使用3种方式指定回退的时间点,SCN,时间,日志序列号,
TO -- 代表回退到指定点
Before -- 代表恢复到指定点之前的一点就可以。
#####################################################
3 、Flashback Drop
#####################################################
这个功能是从Oracle 10g开始出现的,用于恢复用户误删的对象(表,索引)。这个技术依赖于Tablespace Recycle Bin(表空间回收).功能类似于Windows的回收站。
1 Tablespace Recycle Bin
从10g开始,每个表空间都会有一个叫作回收站的逻辑区域(占用表空间所在的空间),当用户执行Drop 命令时,被删除的表和表的关联对象(包括索引,约束,触发器,LOB段,LOB Index段)
不会被物理删除,而是先转移到回收站中,使用Flashback Table命令可以恢复这个对象和所有的关联对象。
不会物理清楚,是不是说明占用的物理空间仍没有释放,从dba_free_space能否反映空间的变化呢?
缺省情况下recyclebin功能是开启的
SQL> show parameter recyclebin
NAME TYPE VALUE
------------------------------------ ----------- ------------------------------
recyclebin string on
show recyclebin 查看Recyclebin的对象列表(注意 RecycleBin是表空间级的,每个表空间都对应一个RecycleBin对象池)
也可以通过视图来查看Recyclebin对象列表
select object_name, original_name from recyclebin;
既然是表空间级的,那这个语句反映的是哪个Recycelbin 池的内容呢?是执行语句的用户的默认表空间吧;
可以像查看普通表一样,查看Recycle Bin中的对象内容
select count(*) from "BIN$jOLWvgYhgyXgQOYKHREVtA==$0";
对Recyclebin中的对象执行DDL/DML动作是不允许的.
SQL> delete from "BIN$jOLWvgYhgyXgQOYKHREVtA==$0";
delete from "BIN$jOLWvgYhgyXgQOYKHREVtA==$0"
*
ERROR at line 1:
ORA-38301: can not perform. DDL/DML over objects in Recycle Bin
2 Flashback Drop 操作
flashback table t to before drop;
如果在recyclebin中有同名的对象,如两个表T都被删除,则恢复:
flashback table "BIN$jOLWvgYhgyXgQOYKHREVtA==$0" to before drop;
在恢复表的同时还可以重命名
flashback table t to before drop rename to t_bak;
Note: 一旦完成恢复,RecycleBin中的对象就消失
3 Recycle Bin的维护
Recycle Bin 是和普通对象共用表空间存储区域的,或者说RecycelBin的对象要和普通对象抢夺存储空间。如果发生空间不够,Oracle会按照先入先出的顺序,
也就是对象被删除的时间顺序覆盖Recycle Bin中的对象。也可以通过如下办法手动清除Recycle Bin占用的空间。
1) #清空某个表空间的RecycleBin池
Purge tablespace tablespace_name;
2) #清空某个表空间内的某个用户的对象
Purge tablespace tablespace_name user user_name;
3) 清除删除当前用户的对象
purge recyclebin
4) 清除所有用户的对象
Purge dba_recyclebin
需要Sysdba权限
5) Drop table xxx purge 永久删除
6) purge index object_name 清除对象的关联索引
4 Flashback Drop 的局限性
Flashback drop 是一个非常实用的技术,减少了很多不完全恢复的需要。 但仍存在一些局限性:
1) 只能用于非系统表空间和本地管理表空间
2) 不能对Recycle Bin中的对象执行DDL,DML操作,只支持查询
3)对象的参考约束不会被恢复,也就是外键约束需要重建
#####################################################
4、 Flashback Query and Flashback Table
#####################################################
这些功能的实现也依赖于Flashback 功能的打开吗?是的;
Flashback Query 实际包含3个工具,即Flashback Query, Flashback Version Query 和 Flashback Transaction Query. 这些工具都是利用Undo的内容来实现回退功能。
前两个属于分析工具,用于找出想要回退到的时间点,而Flashback Table才真正完成回退的操作。
1 Flashback Query
#查询过去某个时间点时的数据
select * from emp as of timestamp to_timestamp('2010-08-03 10:55:15','yyyy-mm-dd hh24:mi:ss');
# 恢复数据
Insert into emp select * from emp as of timestamp to_timestamp('2010-08-03 10:55:15','yyyy-mm-dd hh24:mi:ss');
2 Flashback Version Query
相对于Flashback Query只能看到某一点的对象状态,Oracle 10g引入的Flashback Version Query可以看到过去某个时间段内,记录如何变化的。
根据这个变化的历史,可以决断数据是在什么时间点发生了错误。
#查看表EMP的操作历史
col versions_xid format a16 heading 'XID'
col versions_startscn format 99999999 heading 'Vsn|Start|SCN'
col versions_endscn format 99999999 heading 'Vsn|End|SCN'
col versions_operation format a12 heading 'Operation'
select versions_xid, versions_startscn, versions_endscn,
decode( versions_operation, 'I', 'Insert', 'U', 'Update', 'D', 'Delete', 'Original') "operation",
id, name
from emp
versions between scn minvalue and maxvalue;
注意结果主从下向上看。Original代表最开始的数据。
3 相关的伪列
1) ORA_ROWSCN
记录最后一次被修改时的SCN, 这里的修改是指"被提交的修改",如果没有提交,那么这个伪列不会发生变化。
ORA_ROWSCN 缺省是数据块级别的,也就是一个数据块内的所有记录都是一个ORA_ROWSCN. 数据块内的任意一条记录被修改,这个数据块内的所有记录ORA_ROWSCN都会同时改变。
通过在建表时使用关键字rowdependencies, 可以改变这咱缺省行为。使用这个关键字后,每条记录都有自己的ORA_ROWSCN.
创建表时,如果没有使用rowdependencies关键字,则ORA_ROWSCN使用的是数据块头的SCN,因此在一个数据块内所有记录的ORA_ROWSCN都一样。
如果使用了rowdependencies关键字,则每个记录都有自己的ORA_ROWSCN。这个值来自于ITL或dscn字段。
2)VERSIONS_STARTSCN
表示这行记录获得的值是在哪个SCN获得的,如果为NULL,则表明这一行的值早于versions between scn MINVALUE and MAXVALUE中的MINVALUE。
3) VERSIONS_STARTTIME
同上
4) VERSIONS_ENDSCN
这行记录的这个值是到哪个SCN过期的。
5) VERSIONS_TIME
同上
6) VERSIONS_XID
导致事务修改的事务号
7) VERSIONS_OPERATION
修改类型
U: update
I: insert
D: delete
两个函数:
SCN_TO_TIMESTAMP(current_scn)
select current_scn,scn_to_timestamp(current_scn) curr_time from v$database;
TIMESTAMP_TO_SCN('yyyy-mm-dd hh24:mi:ss1')
Notes
要使用Flashback Version Query, 用户首先要有对象的Select, flashback权限,对表执行过DDL语句之后,就只能查看DDL语句之后的版本,
也就是说Flashback Version Query 不会跨越DDL操作。
Oracle 11g有没有改变,如果可以跨越DDL的话,就可以作为小范围内的审计了;??
4 Flashback Transaction Query
Flashback Transaction Query 与Flashback Version Query类似,也是使用UNDO信息来实现,利用这个功能可以查看某个事务执行的所有变化。
使用这个功能,需要访问Flashback_transaction_query视图
select xid, operation, commit_scn, undo_sql
from flashback_transaction_query
where xid in(
select versions_xid
from emp
versions between scn minvalue and maxvalue);
XID OPERATION COMMIT_SCN UNDO_SQL
---------------- -------------------------------- ---------- --------------------------------------------------------------------------------
0500260003030000 INSERT 2160333 delete from "GZDC"."EMP" where ROWID = 'AAANPcAAEAAAABUAAB';
0500260003030000 BEGIN 2160333
0A00050086020000 INSERT 2160316 delete from "GZDC"."EMP" where ROWID = 'AAANPcAAEAAAABUAAA';
0A00050086020000 INSERT 2160316 delete from "GZDC"."DEP" where ROWID = 'AAANPbAAEAAAABMAAA';
0A00050086020000 BEGIN 2160316
可以看到每个事务的操作历史。
5 Flashback table
Flashback table 真正进行数据的回退。
如果想对表进行Flashback,必须允许row movement.
alter table t1 enable row movement;
flashback table emp,dep to scn xxxx;
6 UNDO Retention
UNDO_RETENTION参数定义的是提交修改后的UNDO记录还要保留多长时间,但是Oracle并不强制保留,如果UNDO空间不够,即使时间没有达到*,这些记录还是会被覆盖。
可以通过在UNDO表空间或者数据库设置Retention Guanrantee来强制保留,缺省没有打开这个功能。
select tablespace_name, retention from dba_tablespaces;
TABLESPACE_NAME RETENTION
------------------------------ -----------
SYSTEM NOT APPLY
UNDOTBS1 NOGUARANTEE
SYSAUX NOT APPLY
TEMP NOT APPLY
USERS NOT APPLY
alter tablespace UNDOTBS1 retention guarantee;
SQL> select tablespace_name, retention from dba_tablespaces;
TABLESPACE_NAME RETENTION
------------------------------ -----------
SYSTEM NOT APPLY
UNDOTBS1 GUARANTEE
SYSAUX NOT APPLY
TEMP NOT APPLY
USERS NOT APPLY
即使强制后,如果空间出现不够时,如何处理?
#####################################################
5 小结
#####################################################
Flashback 家族技术总结:
工具 -- 相关技术 -- 目的
1) Flashback database -- Flashback Log -- 回滚数据库
2) Flashback drop -- Tablespace Bin -- 恢复用户误删的对象
3) Flashback Version Query -- UNDO -- 恢复用户误删的操作
4) Flashback Transaction Query -- UNDO -- 恢复用户误删的操作
5) Flashback table -- UNDO -- 恢复用户误删的操作,在表级别上的操作