Undo segment:
图
1
用于保存一个进程修改了的数据的旧值。
Undo segment
头部包含记录了当前事务使用的
undo segment
信息的一张表。一系列事务只使用一个
undo segment
存储所有数据。许多并发的事务可以使用同一个
undo segment
。
Undo segment
目的:事务回滚、事务恢复、读一致性。
读一致性
:
图
2
每个事务都会分配一个
SCN(system change number)
,
SCN
序号只会增大。当一个查询事务开始时,系统将分配一个比将要查询的表中的
SCN
都大的一个
SCN
。在查表时如果碰到比事务
SCN
大的记录,就会去
undo segment
里查询相应的旧的记录。如果因为时间查询时间太长或其他原因,旧的记录在
undo segment
里被覆盖了的话,查询将失败。
实验
:
以
luo
用户在第一个终端登录:
SQL> select * from test;
ID NAME
---------- --------------------
0 hello
SQL> insert into test values(1, 'world');
1 row created.
SQL> select * from test;
ID NAME
---------- ----------
0 hello
1 world
以
luo
在第二个终端登录:
SQL> select * from test;
ID NAME
---------- --------------------
0 hello
返回第一个终端:
SQL> commit;
Commit complete.
第二个终端:
SQL> select * from test;
ID NAME
---------- --------------------
0 hello
1 world
Redo&undo
:
以
insert
语句为例。
图三
在开始执
insert
时,
Oracle
在内存里产生相应的数据信息、
undo
信息,并且无论是数据,索引还是
undo
都会产生
redo
。如果这时突然断电或
crash
,内存内的数据丢失,但磁盘文件没有被修改。下次启动时不要进行恢复操作。
图四
在把要插入的数据写入磁盘文件之前,先写
redo
。这时如果
crash
了,下次启动将根据
redo
恢复数据。以下的
updata
操作也是同理。
图五
---
图六
Undo segment
类型:
System undo segment
:存在
system
表空间里,
system
表空间专用。
Non-system undo segment
:在存在多个表空间的数据库里,至少需要一个
non-system undo segment
,或手动方式管理或自动方式管理。其中手动方式管理的
undo segment
又分为
private undo segment
和
public undo segment
两种;自动管理方式必须存在一个活动的
undo tablespace
。
Deferred undo segment
:当表空间脱机时可能会创建
deferred undo segment
用于在表空间恢复联机时回滚事务。由
Oracle server
自动管理。
自动
undo segment
管理:
Undo data
在
undo
表空间中被自动管理,
DBA
需根据数据库的负荷给出充足的表空间大小。
参数:
SQL> show parameter undo
NAME TYPE VALUE
------------------------------------ ----------- ------------------------------
undo_management string AUTO
undo_retention integer 10800
undo_suppress_errors boolean FALSE
undo_tablespace string UNDOTBS1
如果管理方式是
auto
并且只存在一个
undo tablespace
,那么
undo_management
是可选项,
the Oracle server will automatically choose the UNDO tablespace.
undo_retention
的值决定了
undo segment
中的数据存储的最长时间,超过这个时间则可能会被其他
undo
数据覆盖。如果
undo segment
没有足够的空间,则
undo
数据即使没过期也可能会被覆盖。这时如果有查询语句可能会导致报错:
ORA-1555 snapshot too old
.
创建
undo
表空间:
SQL> select tablespace_name, contents from dba_tablespaces;
TABLESPACE_NAME CONTENTS
------------------------------ ---------
SYSTEM PERMANENT
UNDOTBS1 UNDO
TEMP TEMPORARY
CWMLITE PERMANENT
DRSYS PERMANENT
EXAMPLE PERMANENT
INDX PERMANENT
ODM PERMANENT
TOOLS PERMANENT
USERS PERMANENT
XDB PERMANENT
TABLESPACE_NAME CONTENTS
------------------------------ ---------
LUO PERMANENT
MYTEMP TEMPORARY
DATA02 PERMANENT
INDEX01 PERMANENT
RONLY PERMANENT
B4K PERMANENT
方法一:
CREATE DATABASE db01
. . .
UNDO TABLESPACE undo1 DATAFILE '/u01/oradata/undoldb01.dbf' SIZE 20M AUTOEXTEND ON
方法二:
CREATE UNDO TABLESPACE undo1 DATAFILE '/u01/oradata/undo1db01.dbf' SIZE 20M;
如果在
create database
时,
undo_management
参数指定为
auto
,但是又省略了
undo tablespace
的句子,那么
Oracle
会自动创建一个
undo tablespace
,命名为
sys_undots
,对应的数据文件:
$ORACLE_HOME/dbs/dbu1sid.dbf.
改变
undo
表空间
:
与其他表空间一样,
undo
表空间可以增删数据文件,重命名,数据文件离线与联机,
begin backup
和
end backup
。
切换
undo
表空间:
可以有多个
undo
表空间,但只有一个是活动的。命令:
ALTER SYSTEM SET UNDO_TABLESPACE=UNDOTBS2;
可以切换当前活动
undo
表空间。
注意:切换表空间后,如果原来的表空间中还有有用的数据,如:事务没用提交,那么原来的表空间还会被使用一段时间(可能是由于
undo_retention
的时间限制),直到所有数据无效。
SQL> select * from test ;
ID NAME
---------- ----------
0 hello
1 world
SQL> insert into test values(2, 'aaa');
1 row created.
SQL> alter system set undo_tablespace='myundo1';
System altered.
SQL> commit;
Commit complete.
SQL> select * from test;
ID NAME
---------- ----------
0 hello
1 world
2 aaa
删除
undo
表空间:
如果
undo
表空间在使用,则不能被
drop
。
Undo
数据统计信息
:
查看当前未提交事务占用的
undo block
数量:
SQL> select addr, used_ublk from v$transaction;
ADDR USED_UBLK
-------- ----------
5AB34700 1
SQL> select begin_time,end_time, undoblks from v$undostat;
下面视图每十分钟记录一次这段时间内使用的
undo block
数量。
BEGIN_TIM END_TIME UNDOBLKS
--------- --------- ----------
02-APR-10 02-APR-10 17
02-APR-10 02-APR-10 19
01-APR-10 02-APR-10 17
01-APR-10 01-APR-10 18
01-APR-10 01-APR-10 18
01-APR-10 01-APR-10 24
01-APR-10 01-APR-10 17
01-APR-10 01-APR-10 19
01-APR-10 01-APR-10 19
01-APR-10 01-APR-10 19
01-APR-10 01-APR-10 14
如果
undo
空间过小,当一个事务需要的
undo
空间不够时则事务处理失败。
估算
undo tablespace
大小:
三个参考值:
(UR)undo_retention
、
(UPS)
每秒产生
undo block
的数量、
(DBS)
块大小。
估算每秒产生
undo block
块数量方法:
方法一:取最大值,
SQL> select max(undoblks / ((end_time - begin_time)*24*3600)) from v$undostat;
MAX(UNDOBLKS/((END_TIME-BEGIN_TIME)*24*3600))
---------------------------------------------
.04
方法
2
:取平均值
SQL> select sum(undoblks) / sum((end_time - begin_time)*24*3600) from v$undostat;
SUM(UNDOBLKS)/SUM((END_TIME-BEGIN_TIME)*24*3600)
------------------------------------------------
.030844624
Segment
大小
=
每秒块数量
*undo_retention*db_block_size
。
Undo
配额:
须额外的包才能提供此功能。
相关视图:
DBA_ROLLBACK_SEGS
V$ROLLNAME
V$ROLLSTAT
V$UNDOSTAT
V$SESSION
V$TRANSACTION
练习:
1
Connect as user
SYSTEM/MANAGER
, and list the undo segments in tablespace
UNDOTBS
.
解析:
SQL> select segment_name, tablespace_name from dba_rollback_segs;
2
Create undo tablespace
UNDO2
, size 15M, in
$HOME/ORADATA/u03
. List the undo
segments in tablespace
UNDO2
.
3
In a new telnet session start SQL*Plus and connect as user
HR
and run script
lab10_03.sql
to insert a row into table
DEPARTMENTS
. Do not commit, roll back, or exit the session.
解析:见上次习题
1.
4
In the session in which you are connected as
SYS
, using the
ALTER SYSTEM
command,switch the
UNDO
tablespace from
UNDOTBS
to
UNDO2
, using
SCOPE=BOTH.
5
As
SYS
,
drop tablespace
UNDOTBS.
Use the
INCLUDING CONTENTS AND DATAFILES
clause
. What happened?
6
List the undo segments in tablespace
UNDOTBS
and their status. Compare this
list to the list in step 1.
Hint:
Query
DBA_ROLLBACK_SEGS
data dictionary view.
7
In the session connected as
HR
, roll back the transaction and exit the session.
8
In the session connected as
SYS
,
drop tablespace
UNDOTBS
. What happened?
9
As
SYS
,
issue the following command:
ALTER SYSTEM SET undo_retention=0 SCOPE=memory;
Now drop tablespace
UNDOTBS
. What happened?
Note:
There still may be a delay before the tablespace is dropped.
本文转自 d185740815 51CTO博客,原文链接:http://blog.51cto.com/luotaoyang/290721,如需转载请自行联系原作者