Oracle 臨時表空間的概念

kakaxi9521發表於2017-04-13
   臨時表空間用來管理資料庫排序操作以及用於儲存臨時表、中間排序結果等臨時物件,當ORACLE裡需要用到SORT的時候,並且當PGA中sort_area_size大小不夠時,將會把資料放入臨時表空間裡進行排序。像資料庫中一些操作: CREATE INDEX、 ANALYZE、SELECT DISTINCT、ORDER BY、GROUP BY、 UNION ALL、 INTERSECT、MINUS、SORT-MERGE JOINS、HASH JOIN等都可能會用到臨時表空間。當操作完成後,系統會自動清理臨時表空間中的臨時物件,自動釋放臨時段。這裡的釋放只是標記為空閒、可以重用,其實實質佔用的磁碟空間並沒有真正釋放。這也是臨時表空間有時會不斷增大的原因。
   臨時表空間儲存大規模排序操作(小規模排序操作會直接在RAM裡完成,大規模排序才需要磁碟排序Disk Sort)和雜湊操作的中間結果.它跟永久表空間不同的地方在於它由臨時資料檔案(temporary files)組成的,而不是永久資料檔案(datafiles)。臨時表空間不會儲存永久型別的物件,所以它不會也不需要備份。另外,對臨時資料檔案的操作不產生redo日誌,不過會生成undo日誌。
  建立臨時表空間或臨時表空間新增臨時資料檔案時,即使臨時資料檔案很大,新增過程也相當快。這是因為ORACLE的臨時資料檔案是一類特殊的資料檔案:稀疏檔案(Sparse File),當臨時表空間檔案建立時,它只會寫入檔案頭部和最後塊資訊(only writes to the header and last block of the file)。它的空間是延後分配的.這就是你建立臨時表空間或給臨時表空間新增資料檔案飛快的原因。
  另外,臨時表空間是NOLOGGING模式以及它不儲存永久型別物件,因此即使資料庫損毀,做Recovery也不需要恢復Temporary Tablespace。

臨時表空間資訊
檢視例項的臨時表空間

SQL1:
SELECT PROPERTY_NAME, PROPERTY_VALUE FROM DATABASE_PROPERTIES WHERE PROPERTY_NAME='DEFAULT_TEMP_TABLESPACE';
SQL2:
SELECT USERNAME, TEMPORARY_TABLESPACE FROM DBA_USERS;

檢視臨時表空間資訊
1. 查v$tempfile

SET LINESIZE 1200
COL NAME FOR A60
SELECT FILE#                        AS FILE_NUMBER
    ,NAME                         AS NAME
    ,CREATION_TIME                   AS CREATION_TIME
    ,BLOCK_SIZE                     AS BLOCK_SIZE
    ,BYTES/1024/1024/1024              AS "FILE_SIZE(G)"
    ,CREATE_BYTES/1024/1024/1024         AS "INIT_SIZE(G)"
    ,STATUS                       AS STATUS
    ,ENABLED                       AS ENABLED
FROM V$TEMPFILE;

2. 查dba_temp_files
SET LINESIZE 1200
COL TABLESPACE_NAME FOR A30
COL FILE_NAME FOR A60
SELECT TABLESPACE_NAME                 AS TABLESPACE_NAME
        ,FILE_NAME                 AS FILE_NAME
        ,BLOCKS                   AS BLOCKS
        ,STATUS                   AS STATUS
        ,AUTOEXTENSIBLE              AS AUTOEXTENSIBLE
        ,BYTES/1024/1024/1024          AS "FILE_SIZE(G)"
        ,DECODE(MAXBYTES, 0, BYTES/1024/1024/1024,
                          MAXBYTES/1024/1024/1024)
                               AS "MAX_SIZE(G)"
        ,INCREMENT_BY               AS "INCREMENT_BY"
        ,USER_BYTES/1024/1024/1024      AS "USEFUL_SIZE"
FROM DBA_TEMP_FILES;

3. 查temp表空間的使用情況
SELECT BYTES,BLOCKS,  USER_BYTES, USER_BLOCKS, BLOCKS -USER_BLOCKS AS SYSTEM_USED FROM DBA_TEMP_FILES;
這四列中, BYTES , BLOCKS 顯示的是臨時檔案有多少BYTE大小,包含多少個資料塊。而USER_BYTES,USER_BLOCKS是可用的BYTE和資料塊個數。因此,我們可以知道臨時檔案中有一部分是被系統佔用的,大概可以理解成檔案頭資訊,這一部分大小是128個block。

管理臨時表空間
1.建立臨時表空間
CREATE TEMPORARY TABLESPACE TMP  
TEMPFILE '/u01/gsp/oradata/TMP01.dbf' 
SIZE 8G
AUTOEXTEND OFF;

2.增加資料檔案
當臨時表空間太小時,就需要擴充套件臨時表空間(新增資料檔案、增大資料檔案、設定檔案自動擴充套件);有時候需要將臨時資料檔案分佈到不同的磁碟分割槽中,提升IO效能,也需要透過刪除、增加臨時表空間資料檔案。
ALTER TABLESPACE TEMP ADD TEMPFILE '/u04/gsp/oradata/temp02.dbf' SIZE 4G AUTOEXTEND ON NEXT 128M MAXSIZE 6G;
ALTER  TABLESPACE TMP ADD TEMPFILE '/u03/eps/oradata/temp02.dbf' SIZE 64G AUTOEXTEND OFF;

3.刪除資料檔案
例如,我想刪除臨時表空間下的某個檔案,那麼我們有兩種方式刪除臨時表空間的資料檔案。

方法1:
ALTER TABLESPACE TEMP DROP TEMPFILE '/u01/app/oracle/oradata/GSP/temp02.dbf';
方法2:
ALTER DATABASE TEMPFILE '/u01/app/oracle/oradata/GSP/temp02.dbf' DROP INCLUDING DATAFILES;
注意:刪除臨時表空間的臨時資料檔案時,不需要指定INCLUDING DATAFILES 選項也會真正刪除物理檔案,否則需要手工刪除物理檔案。

4.調整檔案大小
將臨時資料檔案從1G大小調整為2G
ALTER DATABASE TEMPFILE '/u01/app/oracle/oradata/GSP/temp02.dbf' RESIZE 2G;

5.檔案離線
ALTER DATABASE TEMPFILE '/u01/app/oracle/oradata/GSP/temp02.dbf' OFFLINE;
ALTER DATABASE TEMPFILE '/u01/app/oracle/oradata/GSP/temp02.dbf' ONLINE;
預設臨時表空間不能離線,否則會報錯。

6.設定檔案自動擴充套件
ALTER DATABASE TEMPFILE '/u01/app/oracle/oradata/GSP/temp03.dbf' AUTOEXTEND ON NEXT 100M MAXSIZE UNLIMITED;

7. 移動重新命名檔案
例如,我需要將/u01/app/oracle/oradata/GSP/temp4.dbf這個檔案重新命名為/u01/app/oracle/oradata/GSP/temp04.dbf
1. 將臨時表空間的臨時檔案離線
ALTER DATABASE TEMPFILE '/u01/app/oracle/oradata/GSP/temp4.dbf' OFFLINE;
2. 移動或重新命名相關的臨時檔案
mv /u01/app/oracle/oradata/GSP/temp4.dbf /u01/app/oracle/oradata/GSP/temp04.dbf'
3. 使用指令碼alter database rename file 
ALTER DATABASE RENAME FILE '/u01/app/oracle/oradata/GSP/temp4.dbf' TO '/u01/app/oracle/oradata/GSP/temp04.dbf';
4.將臨時表空間的臨時檔案聯機
ALTER DATABASE TEMPFILE '/u01/app/oracle/oradata/GSP/temp04.dbf' ONLINE;

8.刪除臨時表空間
DROP TABLESPACE TEMP INCLUDING CONTENTS AND DATAFILES CASCADE CONSTRAINTS;
注意: 不能刪除當前使用者的預設表空間,否則會報ORA-12906錯。
如果需要刪除某一個預設的臨時表空間,則必須先建立一個臨時表空間,然後指定新建立的表空間為預設表空間,然後刪除原來的表空間。

臨時表空間租

臨進表空間組:

臨進表空間組是ORACLE 10g引入的一個新特性,它是一個邏輯概念,不需要顯示的建立和刪除。只要把一個臨時表空間分配到一個組中,臨時表空間組就自動建立,所有的臨時表空間從臨時表空間組中移除就自動刪除。

一個臨時表空間組必須由至少一個臨時表空間組成,並且無明確的最大數量限制.

A temporary tablespace group contains at least one tablespace. There is no limit for a group to have a maximum number of tablespaces

如果刪除一個臨時表空間組的所有成員,該組也自動被刪除。

臨時表空間的名字不能與臨時表空間組的名字相同。

It shares the namespace of tablespaces, thus its name cannot be the same as that of any tablespace.

可以在建立臨時表空間是指定表空間組,即隱式建立。

CREATE TEMPORARY TABLESPACE TEMP2 
    TEMPFILE '/u01/app/oracle/oradata/GSP/temp2_1.dbf' SIZE 200M 
    TABLESPACE GROUP GRP_TEMP;
檢視臨時表空間組:
SELECT * FROM DBA_TABLESPACE_GROUPS;

也可以指定已經建立好的臨時表空間的臨時表空間組。
ALTER TABLESPACE  TEMP TABLESPACE GROUP GRP_TEMP;
select * from dba_tablespace_groups;

從組中移除:
ALTER TABLESPACE TEMP TABLESPACE GROUP '';
當為資料庫指定臨時表空間或為使用者指定臨時表空間時,可以使用臨時表空間組的名稱
ALTER USER DM TEMPORARY TABLESPACE GRP_TEMP;


監控臨時表空間

1.檢視臨時表空間使用情況:
SELECT TU.TABLESPACE_NAME                                    AS "TABLESPACE_NAME",
       TT.TOTAL - TU.USED                                    AS "FREE(G)",
       TT.TOTAL                                              AS "TOTAL(G)",
       ROUND(NVL(TU.USED, 0) / TT.TOTAL * 100, 3)            AS "USED(%)",
       ROUND(NVL(TT.TOTAL - TU.USED, 0) * 100 / TT.TOTAL, 3) AS "FREE(%)"
FROM (SELECT TABLESPACE_NAME, 
              SUM(BYTES_USED) / 1024 / 1024 / 1024 USED
       FROM V$TEMP_SPACE_HEADER
       GROUP BY TABLESPACE_NAME) TU ,
     (SELECT TABLESPACE_NAME,
              SUM(BYTES) / 1024 / 1024 / 1024 AS TOTAL
       FROM DBA_TEMP_FILES
       GROUP BY TABLESPACE_NAME) TT
WHERE TU.TABLESPACE_NAME = TT.TABLESPACE_NAME;

################################################################
COL TEMP_FILE FOR A60;
SELECT ROUND((F.BYTES_FREE  + F.BYTES_USED)/1024/1024/1024, 2)                         AS "TOTAL(GB)",
       ROUND(((F.BYTES_FREE  + F.BYTES_USED) - NVL(P.BYTES_USED, 0))/1024/1024/1024,2) AS "FREE(GB)",
       D.FILE_NAME                                                                     AS "TEMP_FILE",
       ROUND(NVL(P.BYTES_USED, 0)/1024/1024/1024, 2)                                   AS "USED(GB)" ,
       ROUND((F.BYTES_USED + F.BYTES_FREE)/1024/1024/1024, 2)                          AS "TOTAL(GB)",
       ROUND(((F.BYTES_USED + F.BYTES_FREE) - NVL(P.BYTES_USED, 0))/1024/1024/1024, 2) AS "FREE(GB)" ,
       ROUND(NVL(P.BYTES_USED, 0)/1024/1024/1024, 2)                                   AS "USED(GB)"
FROM V$TEMP_SPACE_HEADER F ,DBA_TEMP_FILES D ,SYS.V_$TEMP_EXTENT_POOL P
WHERE F.TABLESPACE_NAME(+) = D.TABLESPACE_NAME
  AND F.FILE_ID(+) = D.FILE_ID
  AND P.FILE_ID(+) = D.FILE_ID;

2. 檢視臨時表空間對應的檔案的使用情況
SELECT TABLESPACE_NAME         AS TABLESPACE_NAME    ,
    BYTES_USED/1024/1024/1024    AS TABLESAPCE_USED  ,
    BYTES_FREE/1024/1024/1024  AS TABLESAPCE_FREE
FROM V$TEMP_SPACE_HEADER
ORDER BY 1 DESC;

3. 查詢消耗臨時表空間資源比較多的SQL語句
SELECT   se.username,
         se.sid,
         su.extents,
         su.blocks * to_number(rtrim(p.value)) as Space,
         tablespace,
         segtype,
         sql_text
FROM v$sort_usage su, v$parameter p, v$session se, v$sql s
   WHERE p.name = 'db_block_size'
     AND su.session_addr = se.saddr
     AND s.hash_value = su.sqlhash
     AND s.address = su.sqladdr
ORDER BY se.username, se.sid;



來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/21374452/viewspace-2137181/,如需轉載,請註明出處,否則將追究法律責任。

相關文章