在Oracle 10g數(shù)據(jù)庫中,引入了一個回收站(Recycle Bin)的數(shù)據(jù)庫對象。
回收站,從原理上來說就是一個數(shù)據(jù)字典表,放置用戶Drop掉的數(shù)據(jù)庫對象信息。用戶進(jìn)行Drop操作的對象并沒有被數(shù)據(jù)庫刪除,仍然會占用空間。除非是由于用戶手工進(jìn)行Purge或者因為存儲空間不夠而被數(shù)據(jù)庫清掉。數(shù)據(jù)庫有了這樣的功能,能夠減少很多不必要的麻煩。常常看到開發(fā)人員誤把表刪除,急急忙忙找DBA 來想辦法的情況。相信隨著10G的大范圍應(yīng)用,這種情形應(yīng)該比較少見了,我們可以充分利用10g的閃回(FLASHBACK)功能來避免大量的人工誤操作。
DBA管理上的相關(guān)信息可以從USER_recyclebin(DBA_recyclebin)中獲取。
為了便于測試,我們創(chuàng)建了一個表空間Foo,大小為1M,創(chuàng)建了一個用戶Foo,默認(rèn)的表空間為Foo.
user_recyclebin大多是自解釋的,相對比較容易理解.SQL> CONNECT foo/foo; Connected. SQL> SELECT table_name FROM user_tables; no rows selected SQL> SQL> DESC user_recyclebin Name Null? Type ----------------------------------------- -------- ------------------- OBJECT_NAME NOT NULL VARCHAR2(30) ORIGINAL_NAME VARCHAR2(32) OPERATION VARCHAR2(9) TYPE VARCHAR2(25) TS_NAME VARCHAR2(30) CREATETIME VARCHAR2(19) DROPTIME VARCHAR2(19) DROPSCN NUMBER PARTITION_NAME VARCHAR2(32) CAN_UNDROP VARCHAR2(3) CAN_PURGE VARCHAR2(3) RELATED NOT NULL NUMBER BASE_OBJECT NOT NULL NUMBER PURGE_OBJECT NOT NULL NUMBER SPACE NUMBER SQL>
SQL*Plus命令SHOW recyclebin等價于這條SQL:SQL> SELECT object_name FROM user_recyclebin; no rows selected SQL> SQL> SELECT object_name FROM user_recyclebin; no rows selected SQL> CREATE TABLE foo AS SELECT * FROM DUAL; Table created. SQL> SELECT table_name FROM user_tables; TABLE_NAME ---------------------------------------------- FOO SQL> DROP TABLE foo; Table dropped. SQL> SELECT table_name FROM user_tables; no rows selected SQL> SHOW recyclebin ORIGINAL NAME RECYCLEBIN NAME OBJECT TYPE DROP TIME ---------------- ------------------------------ ------------ ------------------- FOO BIN$V3f/oYUITrCEF2cotS5JaA==$0 TABLE 2004-10-30:14:37:39 SQL>
SQL> SELECT original_name, object_name, TYPE, droptime FROM user_recyclebin; ORIGINAL_NAME OBJECT_NAME TYPE DROPTIME --------------- ------------------------------ ---------- -------------------- FOO BIN$V3f/oYUITrCEF2cotS5JaA==$0 TABLE 2004-10-30:14:37:39 SQL> SQL> DESC "BIN$V3f/oYUITrCEF2cotS5JaA==$0" Name Null? Type ----------------------------------------- -------- ---------------- DUMMY VARCHAR2(1) SQL>
當(dāng)一個表被刪除并移動到"回收站"中,它的名字要進(jìn)行一些轉(zhuǎn)換。這樣的目的顯而易見是為了避免同類對象名稱的重復(fù)。(這一點和Windows操作系統(tǒng)的回收站不同,Windows中的回收站經(jīng)過了特殊的處理,操作系統(tǒng)文件可以重名。)
轉(zhuǎn)換后的名字格式如下:
BIN$unique_id$version
- 其中BIN代表RecycleBin
- unique_id是數(shù)據(jù)庫中該對象的唯一標(biāo)志,26個字符長度
- version表示該對象的版本號
注:在10g beta 版本中,名字格式如下:下面我們驗證一下回收站里數(shù)據(jù)庫對象名字的唯一性:RB$$objn$object_type$version其中的RB,代表Recycle Bin. objn為表的目錄對象號. object_type表示對象類型. version表示版本號. 由數(shù)據(jù)庫指定。
SQL> CREATE TABLE foo AS SELECT * FROM DUAL; Table created. SQL> SELECT table_name FROM user_tables; TABLE_NAME ------------------------------------------------------------ FOO SQL> DROP TABLE foo; Table dropped. SQL> SHOW recyclebin ORIGINAL NAME RECYCLEBIN NAME OBJECT TYPE DROP TIME ---------------- ------------------------------ ------------ ------------------- FOO BIN$VL+ZsqVlQF6R2nYnwAqtvw==$0 TABLE 2004-10-30:15:01:42 FOO BIN$V3f/oYUITrCEF2cotS5JaA==$0 TABLE 2004-10-30:14:37:39 SQL>
能看出來,雖然源表名字相同,在回收站里的對象名字是不同的。
針對Recycle Bin對象的操作
已經(jīng)放到回收站里的表是不能用drop 命令刪除的(注意對象名字上的雙引號):
如果要清掉該對象,使用purge命令:SQL> DROP table "BIN$V3f/oYUITrCEF2cotS5JaA==$0" 2 / DROP table "BIN$V3f/oYUITrCEF2cotS5JaA==$0" * ERROR at line 1: ORA-38301: can not perform DDL/DML over objects in Recycle Bin SQL>
對象已經(jīng)清掉。如果直接清空所有的Recycle Bin中的對象:SQL> PURGE table "BIN$V3f/oYUITrCEF2cotS5JaA==$0" 2 / Table purged. SQL> SELECT object_name, original_name FROM user_recyclebin; OBJECT_NAME ORIGINAL_NAME ------------------------------ --------------- BIN$VL+ZsqVlQF6R2nYnwAqtvw==$0 FOO SQL>
恢復(fù)表,用回閃表的功能:SQL> PURGE RECYCLEBIN; Recyclebin purged. SQL> SELECT object_name, original_name FROM user_recyclebin; no rows selected SQL>
SQL> FLASHBACK TABLE foo TO BEFORE DROP; Flashback complete. SQL>SELECT table_name FROM user_tables; TABLE_NAME ------------------------------------------------------------ FOO SQL>
注:在10g Beta版本中,使用Undrop命令來做到這一點.有的時候,可能同一個名字的表被刪除到回收站中:
SQL> DROP TABLE FOO; Table dropped. SQL> SHOW RECYCLEBIN ORIGINAL NAME RECYCLEBIN NAME OBJECT TYPE DROP TIME ---------------- ------------------------------ ------------ ------------------- FOO BIN$lfTbzOjISXaw8u0BIO7pNA==$0 TABLE 2004-10-30:15:18:03 SQL> CREATE TABLE foo AS SELECT * FROM DUAL; Table created. SQL> DROP TABLE foo; Table dropped. SQL> SHOW RECYCLEBIN ORIGINAL NAME RECYCLEBIN NAME OBJECT TYPE DROP TIME ---------------- ------------------------------ ------------ ------------------- FOO BIN$J63QaUaKTmC1glat+imjeg==$0 TABLE 2004-10-30:15:18:50 FOO BIN$lfTbzOjISXaw8u0BIO7pNA==$0 TABLE 2004-10-30:15:18:03 SQL> FLASHBACK TABLE FOO TO BEFORE DROP; Flashback complete. SQL> SHOW RECYCLEBIN ORIGINAL NAME RECYCLEBIN NAME OBJECT TYPE DROP TIME ---------------- ------------------------------ ------------ ------------------- FOO BIN$lfTbzOjISXaw8u0BIO7pNA==$0 TABLE 2004-10-30:15:18:03 SQL>
默認(rèn)的恢復(fù)是第一個被刪除的FOO表。如果要恢復(fù)指定的表,可以在FLASHBACK TABLE 后面加上指定的RECYCLEBIN 參數(shù)指定其他的名字:
SQL> FLASHBACK TABLE "BIN$lfTbzOjISXaw8u0BIO7pNA==$0" TO BEFORE DROP; FLASHBACK TABLE "BIN$lfTbzOjISXaw8u0BIO7pNA==$0" TO BEFORE DROP * ERROR at line 1: ORA-38312: original name is used by an existing object SQL> FLASHBACK TABLE "BIN$lfTbzOjISXaw8u0BIO7pNA==$0" TO BEFORE DROP 2 RENAME TO foo2; Flashback complete. SQL>