SYSAUX表空間占用過大情況下的處理(AWR信息過多)


SYSAUX表空間占用過大情況下的處理(AWR信息過多)

原創 Oracle 作者:lhrbest 時間:2018-04-12 18:06:04 1748 0 刪除 編輯

SYSAUX表空間占用過大情況下的處理(AWR信息過多)



 

真題1、  SYSTEMSYSAUX表空間存儲的內容有哪些區別?若SYSAUX表空間占用過大則應該如何處理?

答案:在一般情況下,企業產生的業務數據應該存放在單獨的數據表空間,而不應該使用系統已存在的表空間,尤其不能將業務數據保存到SYSTEMSYSAUX表空間中,所以,DBA需要着重關注SYSTEMSYSAUX表空間的占用情況。

Oracle服務器使用SYSTEM表空間管理整個數據庫。這個表空間包含系統的數據字典和關於數據庫的管理信息,這些信息均包含在SYS方案中,只有SYS用戶或者擁有所需權限的其它管理用戶才可訪問這些信息。SYSTEM表空間用於核心功能(例如數據字典表)。

SYSAUXSYSTEM表空間的輔助表空間。Oracle DB早期版本中某些使用SYSTEM表空間或其本身表空間的組件和產品現在改為使用SYSAUX表空間。每個Oracle Database 10g(或更高版本)數據庫都必須擁有SYSAUX表空間。輔助表空間SYSAUX用於附加的數據庫組件,例如,OEM庫(Oracle Enterprise Manager Repository)、AWR快照信息庫、統計信息、審計信息等。

SYSTEMSYSAUX表空間是在創建數據庫時創建的必需存在的表空間。這些表空間必須聯機。在OPEN狀態下,SYSAUX表空間可以脫機以執行表空間恢復,而SYSTEM表空間則不能,這兩種表空間都不能設置為只讀狀態。在MOUNT狀態下,任何表空間都可以脫機。

SYSTEM表空間的大小一般變化不大,而SYSAUX表空間在默認條件下如果不做任何配置,那么隨着時間的推移,會越來越大。所以,如果SYSAUX表空間過大,那么應該及時診斷清理該表空間。

對於SYSTEM表空間而言,如果占用過大,那么一般情況下是由於審計表(SYS.AUD$)過大引起的。需要將審計表移動到其它表空間中,然后再清理審計表(TRUNCATE TABLE SYS.AUD$)即可。需要注意的是,如果審計表過大,那么應該分部去清理審計表,詳細步驟可以參考審計部分。

對於SYSAUX表空間而言,如果占用過大,那么一般情況下是由於AWR信息或對象統計信息沒有及時清理引起的,具體原因可以通過如下的SQL語句查詢:

SELECT OCCUPANT_NAME "Item",

       SPACE_USAGE_KBYTES / 1048576 "Space Used (GB)",

       SCHEMA_NAME "Schema",

       MOVE_PROCEDURE "Move Procedure"

  FROM V$SYSAUX_OCCUPANTS

 WHERE SPACE_USAGE_KBYTES > 1048576

 ORDER BY "Space Used (GB)" DESC;

如果OCCUPANT_NAME列為SM/AWRServer Manageability - Automatic Workload Repository),那么表示AWR信息占用過大;如果該列為SM/OPTSTATServer Manageability - Optimizer Statistics History),那么表示優化器統計信息占用過大。

也可以直接查詢DBA_SEGMENTS視圖獲取信息:

SELECT D.SEGMENT_NAME, D.SEGMENT_TYPE,SUM(BYTES)/1024/1024  SIZE_M

  FROM DBA_SEGMENTS D

 WHERE D.TABLESPACE_NAME = 'SYSAUX'

 GROUP BY D.SEGMENT_NAME, D.SEGMENT_TYPE

 ORDER BY SIZE_M DESC;

然后查詢占用空間較大的表,即可得到占用空間較大的原因,下面分別討論。

(一)AWR信息占用過大

如果確認是AWR信息占用空間過大,那么還可以使用如下的SQL腳本獲取AWR占用信息的詳細信息:

sqlplus / as sysdba @$ORACLE_HOME/rdbms/admin/awrinfo.sql

如果AWR信息占用過大,那么可以通過設置AWR的保留時間來減小AWR信息的存儲空間。通過如下的SQL語句可以獲取AWR的保留時間:

SELECT * FROM DBA_HIST_WR_CONTROL;

通過如下的SQL語句可以設置AWR信息的保留時間為7天(7*24*60),每隔1小時收集一次AWR信息:

EXEC DBMS_WORKLOAD_REPOSITORY.MODIFY_SNAPSHOT_SETTINGS(INTERVAL=>60, RETENTION=>7*24*60);

需要注意的是,在Oracle 10g中,AWR默認保留7天,在Oracle 11g中,AWR默認保留8天。

在以上設置完成后,可以刪除不需要的AWR快照信息,從而釋放SYSAUX表空間,相關SQL語句如下所示:

SELECT MIN(SNAP_ID),MAX(SNAP_ID) FROM DBA_HIST_SNAPSHOT;

SELECT MIN(SNAP_ID),MAX(SNAP_ID) FROM DBA_HIST_ACTIVE_SESS_HISTORY;

BEGIN

     DBMS_WORKLOAD_REPOSITORY.DROP_SNAPSHOT_RANGE(

      LOW_SNAP_ID => 1,

      HIGH_SNAP_ID => 36768,

      DBID => 1148453265);

END;

如果DBMS_WORKLOAD_REPOSITORY.DROP_SNAPSHOT_RANGE執行太慢,那么可以先執行TRUNCATE操作:

select distinct 'truncate  table  '||segment_name||';',s.bytes/1024/1024

  from dba_segments s

 where s.segment_name like 'WRH$%'

   and segment_type in ('TABLE PARTITION', 'TABLE')

   and s.bytes/1024/1024>100

   order by s.bytes/1024/1024/1024 desc;

執行完TRUNCATE操作后,再執行DBMS_WORKLOAD_REPOSITORY.DROP_SNAPSHOT_RANGE。需要注意的是,以上TRUNCATE操作會將AWR中的所有信息全部清除。所以,需要先確認釋放需要這些AWR信息,當然也可以先把需要的AWR信息做導出操作,然后再清空以上AWR信息。

需要注意的是,DBMS_WORKLOAD_REPOSITORY.DROP_SNAPSHOT_RANGE是通過DELETE操作來完全清理工作的。所以,執行完成后,並不會真正的釋放SYSAUX表空間。此時,應該對相關的表執行MOVETRUNCATE操作。在執行MOVE操作時,由於AWR信息的表都是分區表,不能對分區表全表執行MOVE操作,所以需要單獨對分區執行MOVE操作,例如:

ALTER TABLE WRH$_ACTIVE_SESSION_HISTORY MOVE PARTITION 分區名稱;

執行完MOVE操作后,需要對索引進行重建。同理,對於分區索引,只能對分區的單個索引進行重建,而不能總體重建:

ALTER INDEX WRH$_ACTIVE_SESSION_HISTORY_PK REBUILD PARTITION 分區名稱;

需要注意的是,可以在以上SQL后加上“UPDATE GLOBAL INDEXES”子句讓全局索引不失效。

(二)統計信息占用過大

如果統計信息占用空間過大,那么可以修改統計信息的保留時間。統計信息默認保留31天,過期的統計信息會自動被刪除。

SELECT DBMS_STATS.GET_STATS_HISTORY_RETENTION FROM DUAL;  --查詢統計信息的保留時間

EXEC DBMS_STATS.ALTER_STATS_HISTORY_RETENTION(7);  --設置統計信息的保留時間

若發現統計信息占用了SYSAUX上的大量空間,則可以考慮使用DBMS_STATS.PURGE_STATS過程實施清理。

以下的SQL語句對於診斷SYSAUX表空間的占用情況非常有用:

SELECT DBMS_STATS.GET_STATS_HISTORY_AVAILABILITY FROM DUAL;

SELECT MIN(SAVTIME), MAX(SAVTIME) FROM WRI$_OPTSTAT_TAB_HISTORY;

SELECT MIN(SAVTIME), MAX(SAVTIME) FROM SYS.WRI$_OPTSTAT_IND_HISTORY;

SELECT MIN(SAVTIME), MAX(SAVTIME) FROM SYS.WRI$_OPTSTAT_HISTHEAD_HISTORY;

SELECT MIN(SAVTIME), MAX(SAVTIME) FROM SYS.WRI$_OPTSTAT_HISTGRM_HISTORY;

SELECT MIN(SAVTIME), MAX(SAVTIME) FROM SYS.WRI$_OPTSTAT_AUX_HISTORY;

SELECT COUNT(*) FROM SYS.WRI$_OPTSTAT_TAB_HISTORY;

SELECT COUNT(*) FROM SYS.WRI$_OPTSTAT_IND_HISTORY;

SELECT COUNT(*) FROM SYS.WRI$_OPTSTAT_HISTHEAD_HISTORY;

SELECT COUNT(*) FROM SYS.WRI$_OPTSTAT_HISTGRM_HISTORY;

SELECT COUNT(*) FROM SYS.WRI$_OPTSTAT_AUX_HISTORY;

SELECT COUNT(*) FROM SYS.WRI$_OPTSTAT_OPR;

以下SQL可以查詢到無效的ASH信息:

SELECT COUNT(*)

  FROM SYS.WRH$_ACTIVE_SESSION_HISTORY A

 WHERE NOT EXISTS (SELECT 1

          FROM SYS.WRM$_SNAPSHOT B

         WHERE A.SNAP_ID = B.SNAP_ID

           AND A.DBID = B.DBID

           AND A.INSTANCE_NUMBER = B.INSTANCE_NUMBER);

最后需要說明的一點是,負責收集和清理AWR信息的后台進程為MMON,而隱含參數“_swrf_test_action”可以調試MMON的行為,可以和10046事件結合使用。MMON進程每分鍾都會自動刷新一定的AWR數據到磁盤上,默認情況下,MMON30分鍾做一次AWR信息的清理工作。在trace文件中可以看到“MMON Auto-Purge cycle”字樣。

&說明:

有關SYSTEMSYSAUX的更多內容可以參考我的BLOGhttp://blog.itpub.net/26736162/viewspace-2152868/

有關審計的更多內容可以參考我的BLOGhttp://blog.itpub.net/26736162/viewspace-2140644/

有關數據庫操作導致索引失效的更多內容可以參考我的BLOGhttp://blog.itpub.net/26736162/viewspace-2152871/

 

 

 


       




一般來講除開業務數據存放的表空間,DBA要着重關注SYSTEM,SYSAUX,UNDO,TEMP表空間,SYSTEM表空間的大小一般是衡定的,UNDO和TEMP表空間的大小由數據庫的業務情況決定,而SYSAUX表空間在默認條件下你如果不做任何配置,隨着時間的推移,會膨脹的越來越大!SYSAUX表空間做為SYSTEM表空間的輔助表空間,主要存放EM相關的內容以及表統計信息,AWR快照,審計信息等,個人認為,如果你的SYSAUX表空間大小超過2G,那么該考慮讓他減肥了! 

查詢語句:

SELECT D.SEGMENT_NAME, D.SEGMENT_TYPE,SUM(BYTES)/1024/1024  SIZE_M

  FROM DBA_SEGMENTS D

 WHERE D.TABLESPACE_NAME = 'SYSAUX'

 GROUP BY D.SEGMENT_NAME, D.SEGMENT_TYPE

 ORDER BY SIZE_M DESC

查詢出來基本都是AWR的數據,查詢AWR的保留時間:

SELECT * FROM Dba_Hist_Wr_Control;

發現該庫保留了180天約半年的時間,商量之后將該時間縮短至30天:

exec dbms_workload_repository.modify_snapshot_settings(interval=>30, retention=>30*24*60);




一:使用下列語句查詢表空間使用率 
SELECT * FROM ( 
SELECT D.TABLESPACE_NAME, 
        SPACE || 'M' "SUM_SPACE(M)", 
        BLOCKS "SUM_BLOCKS", 
        SPACE - NVL (FREE_SPACE, 0) || 'M' "USED_SPACE(M)", 
        ROUND ( (1 - NVL (FREE_SPACE, 0) / SPACE) * 100, 2) || '%' 
           "USED_RATE(%)", 
        FREE_SPACE || 'M' "FREE_SPACE(M)" 
   FROM (  SELECT TABLESPACE_NAME, 
                  ROUND (SUM (BYTES) / (1024 * 1024), 2) SPACE, 
                  SUM (BLOCKS) BLOCKS 
             FROM DBA_DATA_FILES 
         GROUP BY TABLESPACE_NAME) D, 
        (  SELECT TABLESPACE_NAME, 
                  ROUND (SUM (BYTES) / (1024 * 1024), 2) FREE_SPACE 
             FROM DBA_FREE_SPACE 
         GROUP BY TABLESPACE_NAME) F 
  WHERE D.TABLESPACE_NAME = F.TABLESPACE_NAME(+) 
 UNION ALL                                                           
 SELECT D.TABLESPACE_NAME, 
        SPACE || 'M' "SUM_SPACE(M)", 
        BLOCKS SUM_BLOCKS, 
        USED_SPACE || 'M' "USED_SPACE(M)", 
        ROUND (NVL (USED_SPACE, 0) / SPACE * 100, 2) || '%' "USED_RATE(%)", 
        NVL (FREE_SPACE, 0) || 'M' "FREE_SPACE(M)" 
   FROM (  SELECT TABLESPACE_NAME, 
                  ROUND (SUM (BYTES) / (1024 * 1024), 2) SPACE, 
                  SUM (BLOCKS) BLOCKS 
             FROM DBA_TEMP_FILES 
         GROUP BY TABLESPACE_NAME) D, 
        (  SELECT TABLESPACE_NAME, 
                  ROUND (SUM (BYTES_USED) / (1024 * 1024), 2) USED_SPACE, 
                  ROUND (SUM (BYTES_FREE) / (1024 * 1024), 2) FREE_SPACE 
             FROM V$TEMP_SPACE_HEADER 
         GROUP BY TABLESPACE_NAME) F 
  WHERE D.TABLESPACE_NAME = F.TABLESPACE_NAME(+) 
 ORDER BY 1)  
 WHERE TABLESPACE_NAME IN ('SYSAUX','SYSTEM','UNDOTBS1','TEMP'); 

二:查詢SYSAUX表空間內各個分類項目占存儲空間的比重,很明顯可以看出來AWR快照占用了2G左右的空間,統計信息為149M左右,同時數據庫關閉了審計audit_trail,所以審計表aud$不占空間 
SELECT occupant_name "Item", 
       space_usage_kbytes / 1048576 "Space Used (GB)", 
       schema_name "Schema", 
       move_procedure "Move Procedure" 
  FROM v$sysaux_occupants 
ORDER BY 1 


三:修改統計信息的保持時間,默認為31天,這里修改為7天,過期的統計信息會自動被刪除

SQL> select dbms_stats.get_stats_history_retention from dual; 
 
GET_STATS_HISTORY_RETENTION 
--------------------------- 
                         31 
 
SQL> exec dbms_stats.alter_stats_history_retention(7);       
PL/SQL procedure successfully completed. 
 
SQL> select dbms_stats.get_stats_history_retention from dual; 
 
GET_STATS_HISTORY_RETENTION 
--------------------------- 
                          7 


四:修改AWR快照的保存時間為7天(7*24*60),每小時收集一次,也可以通過EM界面查看和修改

SQL> begin 
         dbms_workload_repository.modify_snapshot_settings ( 
            interval => 60, 
            retention => 10080, 
            topnsql => 100 
          ); 
end; 



五:刪除AWR快照,再次查看SYSAUX表空間使用率,最后表空間使用率降低為38.42%

select min(snap_id),max(snap_id) from dba_hist_snapshot;//查詢最最小和最大快照ID 
 
begin 
     dbms_workload_repository.drop_snapshot_range( 
       low_snap_id => 10758, 
      high_snap_id => 10900, 
      dbid => 387090299); 
end; 


 





以下腳本可以用於診斷SYSAUX表空間使用情況

 

./opatch lsinventory -detail

@?/rdbms/admin/awrinfo

select dbms_stats.get_stats_history_retention from dual;

select dbms_stats.get_stats_history_availability from dual;

select min(SAVTIME), max(SAVTIME) from WRI$_OPTSTAT_TAB_HISTORY;

select min(SAVTIME), max(SAVTIME) from sys.wri$_optstat_ind_history;

select min(SAVTIME), max(SAVTIME) from sys.wri$_optstat_histhead_history;

select min(SAVTIME), max(SAVTIME) from sys.wri$_optstat_histgrm_history;

select min(SAVTIME), max(SAVTIME) from sys.wri$_optstat_aux_history;

select count(*) from sys.wri$_optstat_tab_history;

select count(*) from sys.wri$_optstat_ind_history;

select count(*) from sys.wri$_optstat_histhead_history;

select count(*) from sys.wri$_optstat_histgrm_history;

select count(*) from sys.wri$_optstat_aux_history;

select count(*) from sys.wri$_optstat_opr;




---sysaux表空間占用率很高是awr太多?
select * from dba_hist_wr_control;
 
---30分鍾收集一次,並保留8天時間(單位:分鍾)  interval設置0 表示關閉捕獲快照
exec dbms_workload_repository.modify_snapshot_settings(interval=>30,retention=>8*24*60);
ORA-13541: system moving window baseline size (691200) greater than retention (432000)
ORA-06512: at "SYS.DBMS_WORKLOAD_REPOSITORY", line 174
ORA-06512: at "SYS.DBMS_WORKLOAD_REPOSITORY", line 222
ORA-06512: at line 1
 
 
----查看移動窗口基線大小 MOVING_WINDOW_SIZE=8
select * from dba_hist_baseline;
 
---修改移動窗口基線大小
exec dbms_workload_repository.modify_baseline_window_size(5);
----再執行就不報錯了
exec dbms_workload_repository.modify_snapshot_settings(interval=>30,retention=>5*24*60);
 
---手動創建一個快照
exec dbms_workload_repository.create_snapshot();
 
----創建baseline
exec dbms_workload_repository.create_baseline(56,59,'solgle-db-1');
ORA-13506: operation failed due to invalid snapshot range (56, 59)
ORA-06512: at "SYS.DBMS_WORKLOAD_REPOSITORY", line 281
ORA-06512: at "SYS.DBMS_WORKLOAD_REPOSITORY", line 319
ORA-06512: at line 1
 
----查看所有快照
select * from sys.wrh$_active_session_history order by sample_time desc;
----以某段快照為例,創建基線
exec dbms_workload_repository.create_baseline(2240,2246,'solgle-db-1');
 
---手工刪除某階段快照
exec dbms_workload_repository.drop_snapshot_range(low_snap_id=>2248,high_snap_id=>2249,dbid=>1369758280);
 
----刪除baseline
exec dbms_workload_repository.drop_baseline(baseline_name=>'solgle-db-1',cascade=>true);


若發現statistics統計信息占用了SYSAUX上的大量空間,則可以考慮 使用dbms_stats.purge_stats過程實施清理

 

Modify retention period: DBMS_STATS.ALTER_STATS_HISTORY_RETENTION
Purge old statistics: DBMS_STATS.PURGE_STATS This procedure purges old versions of statistics saved in the dictionary. To run this procedure, you must have the SYSDBA or both ANALYZE ANY DICTIONARY and ANALYZE ANY system privilege.

1. Stats Retention is set to 31 days. By Default it is 7 days. I suggest you can consider reducing the retention days to 10.

2. The number of rows exits in the SYS.WRI$_OPTSTAT_HISTHEAD_HISTORY is 42 Million Rows , where the data exists from “09-JUN-11 01.52.06.895132 PM -05:00 ” to “22-AUG-11 02.53.34.754747 PM -05:00”

3. For other tables ie: SYS. WRI$_OPTSTAT_TAB_HISTORY, SYS.WRI$_OPTSTAT_HISTGRM_HISTORY, the data exists for a month, this is just because the retention set to 31.

ACTION PLAN:
=========

A) Purge the Snapshot . Retain data for 10 days and then purge all the other data. (The number of days data to be kept depends on your Business needs)

SQL> SPOOL CHECK1.OUT

1) Try to force the execution of the purge operations :

SQL> alter session set “_swrf_test_action” = 72;

2) Purging snapshots :

SQL> exec dbms_stats.purge_stats(sysdate-&days);

using &days = n, n-1, n-2, …, n-x

3) Then again execute the below set of SQL’s and upload the spool output file

SQL> SELECT MIN(SAVTIME),MAX(SAVTIME) FROM WRI$_OPTSTAT_TAB_HISTORY;
SQL> SELECT COUNT(*) FROM SYS.WRI$_OPTSTAT_TAB_HISTORY;

SQL> SELECT MIN(SAVTIME), MAX(SAVTIME) FROM SYS.WRI$_OPTSTAT_HISTHEAD_HISTORY;
SQL> SELECT COUNT(*) FROM SYS.WRI$_OPTSTAT_HISTHEAD_HISTORY;

SQL> SELECT MIN(SAVTIME), MAX(SAVTIME) FROM SYS.WRI$_OPTSTAT_HISTGRM_HISTORY;
SQL> SELECT COUNT(*) FROM SYS.WRI$_OPTSTAT_HISTGRM_HISTORY;

SQL> SPOOL OFF

B) Change the No. of Retention days from 31 to 10. For performing the same, use the below command : (The new retention time is specified in minutes.)

SQL> exec dbms_workload_repository.modify_snapshot_settings(retention=>14400);

NOTE : The parameter value is in minutes so 10 daysx 24 hours x 60 minutes = 14400 minutes

C) Check the value of STATISTICS_LEVEL

If the above value is Set to ALL, then consider changing to TYPICAL.

The reason for requesting to change it to TYPICAL , is because statistics_level=ALL will gather lot of additional information in AWR repository which would consume more space.

Most of the cases, if the statistics_level is set to TYPICAL then the growth would be stopped.

Once the above actions performed, please keep us posted on the status of the same



Oracle 11g 清理SYSAUX空間

SYSAUX表空間做為SYSTEM表空間的輔助表空間,主要存放EM相關的內容以及表統計信息,AWR快照,審計信息等。今天就碰到了這個問題,數據庫較慢,奇怪的是無法獲取AWR報告。

SQL> select * from v$version;

BANNER
--------------------------------------------------------------------------------
Oracle Database 11g Enterprise Edition Release 11.2.0.4.0 - 64bit Production
PL/SQL Release 11.2.0.4.0 - Production
CORE    11.2.0.4.0      Production
TNS for Linux: Version 11.2.0.4.0 - Production
NLSRTL Version 11.2.0.4.0 - Production

--截取獲取數據庫報告的片段,正常是顯示快照id

輸入 num_days 的值:  1
Listing the last 1 days of Completed Snapshots
--手工生成快照保存,很明顯是表空間不足
SQL> exec dbms_workload_repository.create_snapshot();
BEGIN dbms_workload_repository.create_snapshot(); END;
*
第 1 行出現錯誤:
ORA-13509: 更新 AWR 表時出錯
ORA-01683: 索引 ORA-01683: 索引 SYS.WRH$_ACTIVE_SESSION_HISTORY_PK 分區 WRH$_ACTIVE_1148453265_0 無法通過 8192 (在表空間 SYSAUX 中) 擴展
. 分區  無法通過  (在表空間  中) 擴展
ORA-06512: 在 "SYS.DBMS_WORKLOAD_REPOSITORY", line 99
ORA-06512: 在 "SYS.DBMS_WORKLOAD_REPOSITORY", line 122
ORA-06512: 在 line 1
--查詢SYSAUX表空間的使用情況,消耗37G,快滿了
SQL> SELECT Upper(F.TABLESPACE_NAME)         "表空間名",
           D.TOT_GROOTTE_MB                 "表空間大小(M)",
           D.TOT_GROOTTE_MB - F.TOTAL_BYTES "已使用空間(M)",
           To_char(Round(( D.TOT_GROOTTE_MB - F.TOTAL_BYTES ) / D.TOT_GROOTTE_MB * 100, 2), '990.99')
           || '%'                           "使用比",
           F.TOTAL_BYTES                    "空閑空間(M)",
           F.MAX_BYTES                      "最大塊(M)"
    FROM   (SELECT TABLESPACE_NAME,
                   Round(Sum(BYTES) / ( 1024 * 1024 ), 2) TOTAL_BYTES,
                   Round(Max(BYTES) / ( 1024 * 1024 ), 2) MAX_BYTES
            FROM   SYS.DBA_FREE_SPACE
            GROUP  BY TABLESPACE_NAME) F,
           (SELECT DD.TABLESPACE_NAME,
                   Round(Sum(DD.BYTES) / ( 1024 * 1024 ), 2) TOT_GROOTTE_MB
            FROM   SYS.DBA_DATA_FILES DD
            GROUP  BY DD.TABLESPACE_NAME) D
    WHERE  D.TABLESPACE_NAME = F.TABLESPACE_NAME
    and D.tablespace_name = 'SYSAUX';
表空間名  表空間大小(M) 已使用空間(M) 使用比   空閑空間(M)  最大塊(M)
--------- ------------- ------------- -------- ----------- ----------
SYSAUX         37887.98       37865.6   99.94%       22.38          1
--查看SYSAUX表空間表的使用情況
SQL> select *
       from (select segment_name,
                    segment_type,
                    bytes / 1024 / 1024
               from dba_segments
              where tablespace_name = 'SYSAUX'
              and bytes / 1024 / 1024 >1000
              order by bytes desc);
SEGMENT_NAME                          SEGMENT_TYPE       BYTES/1024/1024
------------------------------------- ------------------ ---------------
WRH$_ACTIVE_SESSION_HISTORY           TABLE PARTITION       13479
I_WRI$_OPTSTAT_H_OBJ#_ICOL#_ST        INDEX                 2590
WRI$_OPTSTAT_HISTGRM_HISTORY          TABLE                 2242
WRH$_EVENT_HISTOGRAM_PK               INDEX PARTITION       1856
WRH$_EVENT_HISTOGRAM                  TABLE PARTITION       1792
I_WRI$_OPTSTAT_H_ST                   INDEX                 1544
WRH$_ACTIVE_SESSION_HISTORY_PK        INDEX PARTITION       1472
WRH$_LATCH                            TABLE PARTITION       1155


--使用dbms_workload_repository.drop_snapshot_range可以刪除歷史數據,怎奈太慢了,半個小時完全沒有反映。通過v$session看到執行的SQL是delete,這種做法無法降低高水位線。

SQL> select min(snap_id),max(snap_id) from dba_hist_snapshot;
MIN(SNAP_ID) MAX(SNAP_ID)
------------ ------------
SQL> select min(snap_id),max(snap_id) from dba_hist_active_sess_history;
MIN(SNAP_ID) MAX(SNAP_ID)
------------ ------------
1             36768
SQL> begin 
     dbms_workload_repository.drop_snapshot_range( 
      low_snap_id => 1, 
      high_snap_id => 36768, 
      dbid => 1148453265); 
end; 


--手工生成truncate,需要在SYS下執行

select distinct 'truncate  table  '||segment_name||';',s.bytes/1024/1024
  from dba_segments s
 where s.segment_name like 'WRH$%'
   and segment_type in ('TABLE PARTITION', 'TABLE')
   and s.bytes/1024/1024>100
   order by s.bytes/1024/1024/1024 desc;
   
--執行完成后,看效果
SQL> SELECT Upper(F.TABLESPACE_NAME)         "表空間名",
          D.TOT_GROOTTE_MB                 "表空間大小(M)",
          D.TOT_GROOTTE_MB - F.TOTAL_BYTES "已使用空間(M)",
          To_char(Round(( D.TOT_GROOTTE_MB - F.TOTAL_BYTES ) / D.TOT_GROOTTE_MB * 100, 2), '990.99')
          || '%'                           "使用比",
          F.TOTAL_BYTES                    "空閑空間(M)",
          F.MAX_BYTES                      "最大塊(M)"
   FROM   (SELECT TABLESPACE_NAME,
                  Round(Sum(BYTES) / ( 1024 * 1024 ), 2) TOTAL_BYTES,
                  Round(Max(BYTES) / ( 1024 * 1024 ), 2) MAX_BYTES
           FROM   SYS.DBA_FREE_SPACE
           GROUP  BY TABLESPACE_NAME) F,
          (SELECT DD.TABLESPACE_NAME,
                  Round(Sum(DD.BYTES) / ( 1024 * 1024 ), 2) TOT_GROOTTE_MB
           FROM   SYS.DBA_DATA_FILES DD
           GROUP  BY DD.TABLESPACE_NAME) D
   WHERE  D.TABLESPACE_NAME = F.TABLESPACE_NAME
   and D.tablespace_name = 'SYSAUX';
表空間名  表空間大小(M) 已使用空間(M) 使用比   空閑空間(M)  最大塊(M)
--------- ------------- ------------- -------- ----------- ----------
SYSAUX         37887.98       9132.67   24.10%    28755.31        544



 

不知何時何原因,一個數據庫的AWR不自動刪除了,然后慢慢的SYSAUX表空間滿了,alert日志也開始報警

其主要是WRH$_ACTIVE_SESSION_HISTORY 的一個分區表占了很多,沒遇到過的問題,總是感覺很緊張,尤其又是生產庫

於是乎,想了個笨方法開始手動刪WRH$_ACTIVE_SESSION_HISTORY的數據,刪的差不多了就開始收縮表,收縮完表空間有地了

可是過段時間又滿了,心想這笨方法可不行,開始找方法

在官方發現文檔 387914.1就是說的這個問題

WRH$_ACTIVE_SESSION_HISTORY Does Not Get Purged Based Upon the Retention Policy (文檔 ID 387914.1)

In this Document

  Symptoms
  Cause
  Solution
  Community Discussions
  References

 

APPLIES TO:

Oracle Database - Enterprise Edition - Version 10.2.0.1 and later
Information in this document applies to any platform.

SYMPTOMS

AWR tables are not being purged according to settings in sys.wrm$_wr_control. Because of this the tables are accumulating more and more rows and the segments associated with these tables become very large.

CAUSE

Oracle decides what rows need to be purged based on the retention policy. There is a special mechanism which is used in the case of the large AWR tables where we store the snapshot data in partitions. One method of purging data from these tables is by removing partitions that only contain rows that have exceeded the retention criteria. During the nightly purge task, we only drop the partition if all the data in the partition has expired. If the partition contains at least one row which, according to the retention policy shouldn't be removed,  then  the partition won't be dropped and as such the table will contain old data.

If partition splits do not occur (for whatever reason), then we can end up with a situation where we have to wait for the latest entries to expire before the partition that they sit in can be removed. This can mean that some of the older entries can be retained significantly past their expiry date. The result of this is that the data is not purged as expected.

SOLUTION

A potential solution to this issue is to manually split the partitions of the partitioned AWR objects such that there is more chance of the split partition being purged.You will still have to wait for all the rows in the new partitions to reach their retention time but with split partitions there is more chance of this happening. you can manually split the partitions using the following undocumented command:

alter session set "_swrf_test_action" = 72;

To perform a single split of all the AWR partitions.

  1.  Check the partition details for the offending table before the split:   
     SELECT owner,
      segment_name,
      partition_name,
      segment_type,
      bytes/1024/1024/1024 Size_GB
    FROM dba_segments
    WHERE segment_name='WRH$_ACTIVE_SESSION_HISTORY';
  2. Split the partitions so that there is more chance of the smaller partition being purged:
    alter session set "_swrf_test_action" = 72;
    NOTE:  This command will split partitions for ALL partitioned AWR objects. It also initiates a single split; it does not need to be disabled and will need to be repeated if multiple splits are required.
      

  3.  Check the partition details for the offending table after the split:      
    SELECT owner,
      segment_name,
      partition_name,
      segment_type,
      bytes/1024/1024/1024 Size_GB
    FROM dba_segments
    WHERE segment_name='WRH$_ACTIVE_SESSION_HISTORY';


    With smaller partitions it is expected that some will be automatically removed when the retention period of all the rows within each partition is reached.


As an alternative, you could purge data based upon a snapshot range. Depending on the snapshots chosen, this may remove data that has not yet reached the retention limit so this may not be suitable for all cases. 

The following output shows the min and max snapshot_id in each partition.

set serveroutput on 
declare 
CURSOR cur_part IS 
SELECT partition_name from dba_tab_partitions 
WHERE table_name = 'WRH$_ACTIVE_SESSION_HISTORY'; 

query1 varchar2(200); 
query2 varchar2(200); 

TYPE partrec IS RECORD (snapid number, dbid number); 
TYPE partlist IS TABLE OF partrec; 

Outlist partlist; 
begin 
dbms_output.put_line('PARTITION NAME SNAP_ID DBID'); 
dbms_output.put_line('--------------------------- ------- ----------'); 

for part in cur_part loop 
query1 := 'select min(snap_id), dbid from sys.WRH$_ACTIVE_SESSION_HISTORY partition ('||part.partition_name||') group by dbid'; 
execute immediate query1 bulk collect into OutList; 

if OutList.count > 0 then 
for i in OutList.first..OutList.last loop 
dbms_output.put_line(part.partition_name||' Min '||OutList(i).snapid||' '||OutList(i).dbid); 
end loop; 
end if; 

query2 := 'select max(snap_id), dbid from sys.WRH$_ACTIVE_SESSION_HISTORY partition ('||part.partition_name||') group by dbid'; 
execute immediate query2 bulk collect into OutList; 

if OutList.count > 0 then 
for i in OutList.first..OutList.last loop 
dbms_output.put_line(part.partition_name||' Max '||OutList(i).snapid||' '||OutList(i).dbid); 
dbms_output.put_line('---'); 
end loop; 
end if; 

end loop; 
end; 
/


Once you have split the partitions and identified a partition with a range of snap ids that can be deleted, you can free up the memory by dropping a snapshot range than matches the high and low snap_ids for the partition:

DBMS_WORKLOAD_REPOSITORY.DROP_SNAPSHOT_RANGE( 
low_snap_id IN NUMBER, 
high_snap_id IN NUMBER 
dbid IN NUMBER DEFAULT NULL);

 


其方法就是執行alter session set "_swrf_test_action" = 72; 讓AWR相關的分區表都創建一個新的分區,等待老分區的數據過期,oracle就會自動刪除。

可眼下表空間已經滿了,等不到老分區的數據過期,可咋辦

那么可以先修改AWR的有效保留期,比如改成5天。等5天后oracle刪掉分區在把保留期改回來。如果老數據需要保留可以導出AWR的信息。



流言終結者: AWR的保留天數和SYSAUX表空間的使用率有關嗎?

雖然不知道以上這番理論出自那部書籍,但是至少是說的有模有樣的,而且網友還告訴我這是他測試過的結果。

實際是這樣嗎?

我相信這位網友並沒有吹牛,他很可能查詢dba_hist_snapshot等AWR視圖且看到了的確有7天之前的快照仍被保留着,而沒有被清理掉。我們來重演他所看到的現場:

測試使用版本11.2.0.2 , 11g中默認AWR保留8天:

 

SQL> select * from v$version;

BANNER
--------------------------------------------------------------------------------
Oracle Database 11g Enterprise Edition Release 11.2.0.2.0 - 64bit Production
PL/SQL Release 11.2.0.2.0 - Production
CORE    11.2.0.2.0      Production
TNS for Linux: Version 11.2.0.2.0 - Production
NLSRTL Version 11.2.0.2.0 - Production

SQL> select * from global_name;

GLOBAL_NAME
----------------------------------------------------------
www.askmaclean.com & www.askmaclean.com

SQL> col SNAP_INTERVAL for a20
SQL> col RETENTION for a20
SQL> select snap_interval,retention from dba_hist_wr_control;

SNAP_INTERVAL        RETENTION
-------------------- --------------------
+00000 01:00:00.0    +00008 00:00:00.0

以上確認了默認的快照間隔為1小時 ,且保留時間為8天

檢查當前SYSAUX表空間的使用率

REM tablespace report

set linesize 200

select a.tablespace_name,
       round(a.bytes_alloc / 1024 / 1024) megs_alloc,
       round(nvl(b.bytes_free, 0) / 1024 / 1024) megs_free,
       round((a.bytes_alloc - nvl(b.bytes_free, 0)) / 1024 / 1024) megs_used,
       round((nvl(b.bytes_free, 0) / a.bytes_alloc) * 100) Pct_Free,
       100 - round((nvl(b.bytes_free, 0) / a.bytes_alloc) * 100) Pct_used,
       round(maxbytes / 1048576) Max
  from (select f.tablespace_name,
               sum(f.bytes) bytes_alloc,
               sum(decode(f.autoextensible, 'YES', f.maxbytes, 'NO', f.bytes)) maxbytes
          from dba_data_files f
         group by tablespace_name) a,
       (select f.tablespace_name, sum(f.bytes) bytes_free
          from dba_free_space f
         group by tablespace_name) b
 where a.tablespace_name = b.tablespace_name(+)
union all
select h.tablespace_name,
       round(sum(h.bytes_free + h.bytes_used) / 1048576) megs_alloc,
       round(sum((h.bytes_free + h.bytes_used) - nvl(p.bytes_used, 0)) /
             1048576) megs_free,
       round(sum(nvl(p.bytes_used, 0)) / 1048576) megs_used,
       round((sum((h.bytes_free + h.bytes_used) - nvl(p.bytes_used, 0)) /
             sum(h.bytes_used + h.bytes_free)) * 100) Pct_Free,
       100 -
       round((sum((h.bytes_free + h.bytes_used) - nvl(p.bytes_used, 0)) /
             sum(h.bytes_used + h.bytes_free)) * 100) pct_used,
       round(sum(f.maxbytes) / 1048576) max
  from sys.v_$TEMP_SPACE_HEADER h,
       sys.v_$Temp_extent_pool  p,
       dba_temp_files           f
 where p.file_id(+) = h.file_id
   and p.tablespace_name(+) = h.tablespace_name
   and f.file_id = h.file_id
   and f.tablespace_name = h.tablespace_name
 group by h.tablespace_name
 ORDER BY 1
/

TABLESPACE_NAME                MEGS_ALLOC  MEGS_FREE  MEGS_USED   PCT_FREE   PCT_USED        MAX
------------------------------ ---------- ---------- ---------- ---------- ---------- ----------
MGMT_AD4J_TS                          200        199          1         99          1      32768
MGMT_ECM_DEPOT_TS                      40         13         27         32         68      32768
MGMT_TABLESPACE                      1350         86       1265          6         94      32768
SYSAUX                                600        295        305         49         51      32768
SYSTEM                                700        231        469         33         67      32768
TEMP                                   21         21          0        100          0      32768
UNDOTBS1                              495        358        137         72         28      32768
USERS                                1950       1243        707         64         36      32768

SYSAUX表空間剩余295MB空間,空閑率較高

 

因為這套數據庫在2011-10-17之后就一直沒有打開過,所以Automatic Workload Repository中最早保留的快照信息是在2011-10-10,通過查詢dba_hist_snapshot視圖可以反映這一點:

 

select snap_id,
       to_char(begin_interval_time, 'YYYY-MM-DD'),
       to_char(end_interval_time, 'YYYY-MM-DD')
  from dba_hist_snapshot
 order by snap_id;
   SNAP_ID TO_CHAR(BE TO_CHAR(EN
---------- ---------- ----------
        96 2011-10-10 2011-10-10
        97 2011-10-10 2011-10-10
        98 2011-10-10 2011-10-10
        99 2011-10-10 2011-10-10
       100 2011-10-10 2011-10-10
       101 2011-10-10 2011-10-11
       102 2011-10-11 2011-10-11
       103 2011-10-11 2011-10-11
...................
       221 2011-10-17 2011-10-17
       222 2011-10-24 2011-10-24

SQL> select sysdate from dual;

SYSDATE
---------
24-OCT-11

 

當前的日期是24-OCT-11,而最早的快照信息是在2011-10-10,這樣就達成了網友所說的AWR的保留時間並非7或8天,”awr保留天數根據sysaux大小決定。” 或 “默認7天,sysaux足夠大這個7天沒有意義” 的說法。

 

事實是這樣嗎?

不是的!

那么為什么能看到早於7天的快照呢?

回答: 不要被所看到的信息所蒙蔽,雖然我們常說事實勝於雄辯或實踐是檢驗真知的唯一 , 但事情的表象往往會欺騙我們。

以上這個問題的關鍵點並非在於是否能看到早於7天的snapshot快照信息,而在於當MMON后台進程(該進程負責收集和清理AWR數據)在執行對過期快照清理工作時是否會清除7 或 8 天之前的snapshot,以及MMON后台進程多久才Purge一次AWR Snapshot。

以上這些問題 , 我們可以通過_swrf_test_action參數和10046 trace搞清楚:

 

SQL> SELECT x.ksppinm NAME, y.ksppstvl VALUE, x.ksppdesc describ
  2   FROM SYS.x$ksppi x, SYS.x$ksppcv y
  3   WHERE x.inst_id = USERENV ('Instance')
  4   AND y.inst_id = USERENV ('Instance')
  5   AND x.indx = y.indx
  6  AND x.ksppinm LIKE '%_swrf%';

NAME                 VALUE      DESCRIB
-------------------- ---------- --------------------------------------------------
_swrf_test_action    0          test action parameter for SWRF
_swrf_mmon_flush     TRUE       Enable/disable SWRF MMON FLushing
_swrf_mmon_metrics   TRUE       Enable/disable SWRF MMON Metrics Collection
_swrf_metric_frequen FALSE      Enable/disable SWRF Metric Frequent Mode Collectio
t_mode                          n

_swrf_on_disk_enable TRUE       Parameter to enable/disable SWRF
d

_swrf_mmon_dbfus     TRUE       Enable/disable SWRF MMON DB Feature Usage
_swrf_test_dbfus     FALSE      Enable/disable DB Feature Usage Testing

 

_swrf_test_action 隱藏參數用以調試MMON的行為,設置該參數並10046事件:

 

SQL> alter session set "_swrf_test_action" = 28; 

Session altered.

SQL> alter session set "_swrf_test_action" = 10; 

Session altered.

[oracle@vrh4 ContentsXML]$ ps -ef|grep mmon
oracle    2872     1  0 18:28 ?        00:00:00 ora_mmon_SBDB
oracle    3446  3289  0 18:44 pts/1    00:00:00 tail -f SBDB_mmon_2872.trc
oracle    3997  3407  0 19:17 pts/2    00:00:00 grep mmon

SQL> oradebug setospid 2872;
Oracle pid: 15, Unix process pid: 2872, image: oracle@vrh4.oracle.com (MMON)

SQL> oradebug event 10046 trace name context forever,level 12;
Statement processed.

 

完成以上操作后等待一段時間,MMON進程的trace文件會陸續寫出一些信息,如:

 

*** 2011-10-24 18:45:24.795
KEWRAFM: Beginning one MMON Auto-Flush cycle ...
  Finished one MMON Auto-Flush cycle.

*** 2011-10-24 18:46:24.874
KEWRAFM: Beginning one MMON Auto-Flush cycle ...
  Finished one MMON Auto-Flush cycle.

*** 2011-10-24 18:47:24.952
KEWRAFM: Beginning one MMON Auto-Flush cycle ...
  Finished one MMON Auto-Flush cycle.

*** 2011-10-24 18:48:25.053
KEWRAFM: Beginning one MMON Auto-Flush cycle ...
  Finished one MMON Auto-Flush cycle.

說明MMON每分鍾都會自動刷新一定的數據到磁盤上。

 

此外還可以看到MMON清理過期快照的信息:

 

*** 2011-10-24 18:58:25.290
KEWRAFM: Beginning one MMON Auto-Flush cycle ...
  Finished one MMON Auto-Flush cycle.
KEWRAPM: Beginning one MMON Auto-Purge cycle ... KEWRAPM: Finished one MMON Auto-Purge cycle. KEWRAPC: Auto Purge Action Completed.

*** 2011-10-24 19:28:26.091
KEWRAFM: Beginning one MMON Auto-Flush cycle ...
  Finished one MMON Auto-Flush cycle.
KEWRAPM: Beginning one MMON Auto-Purge cycle ..
  KEWRAPM: Finished one MMON Auto-Purge cycle

*** 2011-10-24 19:58:27.041
KEWRAFM: Beginning one MMON Auto-Flush cycle ...
  Finished one MMON Auto-Flush cycle.
KEWRAPM: Beginning one MMON Auto-Purge cycle ...
  KEWRAPM: Finished one MMON Auto-Purge cycle.

 

可以看到在默認情況下MMON每30分鍾會自動去清理一次Automatic Workload Repository自動負載倉庫中的過期快照信息,當18:58:25.290的第一次清理工作完成后查詢dba_hist_snapshot可以發現過期快照消失了:

 

SQL> select snap_id,
  2         to_char(begin_interval_time, 'YYYY-MM-DD'),
  3         to_char(end_interval_time, 'YYYY-MM-DD')
  4    from dba_hist_snapshot
  5   order by snap_id;

   SNAP_ID TO_CHAR(BE TO_CHAR(EN
---------- ---------- ----------
       194 2011-10-16 2011-10-16
       195 2011-10-16 2011-10-16
       196 2011-10-16 2011-10-16
       197 2011-10-16 2011-10-16
.................
       222 2011-10-24 2011-10-24

 

通過以上演示我們可知AWR快照的保留天數與SYSAUX的使用率並無關系,實際控制AWR保留天數的最主要因素是MMON何時、如何地清理過期快照? MMON的清理操作直接受到dba_hist_wr_control.retention設置值的影響,默認情況10g 為保留7天,而11g為保留8天,MMON只已清理過期的快照。

同時KEWRAPM的trace信息也說明了,默認情況下MMON每30分鍾做一次”MMON Auto-Purge cycle”清理工作。



二、清理SYAUX下的無效ASH信息

1.檢查是否有無效的ASH信息
select count(*)
from sys.wrh$_active_session_history a
where not exists (select 1
from sys.wrm$_snapshot b
where a.snap_id = b.snap_id
and a.dbid = b.dbid
and a.instance_number = b.instance_number);
2.清理無效的ASH信息
delete
from sys.wrh$_active_session_history a
where not exists (select 1
from sys.wrm$_snapshot b
where a.snap_id = b.snap_id
and a.dbid = b.dbid
and a.instance_number = b.instance_number);
3.對ASH表清理后的碎片整理
alter table sys.wrh$_active_session_history enable row movement;
alter table sys.wrh$_active_session_history shrink space cascade;
alter table sys.wrh$_active_session_history disable row movement;
4.收集碎片整理后表的統計信息
EXEC dbms_stats.gather_table_stats(ownname => ‘SYS’,tabname => ‘WRH$_ACTIVE_SESSION_HISTORY’,cascade => TRUE);
3.檢查表空間可收縮的的位置
select a.FILE#,
a.NAME,
a.BYTES / 1024 / 1024 mb,
ceil(HWM * A.BLOCK_SIZE) / 1024 / 1024 RESIZETO,
‘ALTER DATABASE DATAFILE ”’ || A.NAME || ”’ RESIZE ‘ ||
(trunc(CEIL(HWM * A.BLOCK_SIZE) / 1024 / 1024)+20) || ‘M;’ RESIZECMD
from v$datafile a,
(SELECT C.file_id, MAX(C.block_id + C.blocks – 1) HWM
FROM DBA_EXTENTS C
GROUP BY FILE_ID) B
WHERE A.FILE# = B.FILE_ID
AND a.tablespace=’SYSAUX’
ORDER BY 5;

三.SYSAUX清理后的檢查

1.清理后的無效INDEX檢查
select * from dba_indexes where status<>‘VALID’ AND STATUS<>‘N/A’;
SELECT * FROM DBA_IND_PARTITIONS WHERE STATUS<>‘USABLE’ AND STATUS<>‘N/A’;
SELECT * FROM DBA_IND_SUBPARTITIONS WHERE STATUS<>‘USABLE’;
上面語句應均無數據返回,如有則對這些INDEX進行重建
2.清理后的INDEX並行度檢查
select * from dba_indexes where degree not in (’1′,’0′,’DEFAULT’);



   

oracle數據庫清理和回收system和sysaux表空間

作者:dbdream   

 
前幾天和一個網友討論了下SYSAUX表空間使用率過高的問題,今天有時間整理一下,正好我們的測試數據庫也存在這個問題。本案例數據庫版本為11.2.0.4.0。
SYSAUX表空間被稱為系統輔助表空間,是10g版本開始推出的新功能,主要的目的是為SYSTEM表空間減負,Oracle對SYSTEM表空間的維護有一套獨立的體系,對SYSTEM表空間操作會占用額外的CPU資源,而且效率低下,詳見我之前發表的文章為什么不要把用戶表存儲到SYSTEM表空間。在10g版本,增加了SYSAUX輔助表空間,將EM、AWR等組件的表從SYSTEM表空間挪到了SYSAUX表空間中,這樣大大減少了SYSTEM表空間的消耗,也減少了Oracle對SYSTEM表空間維護的成本。
但是有幾個比較坑爹的組件需要的表並沒有挪到SYSAUX表空間,比如常見的審計用到的AUD$表,很多DBA都可能遇到SYSTEM表空間使用率過高,查詢發現是AUD$表很大導致的,我們的數據庫正好打開了審計功能,正好可以拿來做實驗。
下面先查詢下SYSTEM和SYSAUX表空間的使用率。
sys@IVLDB> SELECT * FROM (
  2  SELECT D.TABLESPACE_NAME,
  3          SPACE || 'M' "SUM_SPACE(M)",
  4          BLOCKS "SUM_BLOCKS",
  5          SPACE - NVL (FREE_SPACE, 0) || 'M' "USED_SPACE(M)",
  6          ROUND ( (1 - NVL (FREE_SPACE, 0) / SPACE) * 100, 2) || '%'
  7             "USED_RATE(%)",
  8          FREE_SPACE || 'M' "FREE_SPACE(M)"
  9     FROM (  SELECT TABLESPACE_NAME,
 10                    ROUND (SUM (BYTES) / (1024 * 1024), 2) SPACE,
 11                    SUM (BLOCKS) BLOCKS
 12               FROM DBA_DATA_FILES
 13           GROUP BY TABLESPACE_NAME) D,
 14          (  SELECT TABLESPACE_NAME,
 15                    ROUND (SUM (BYTES) / (1024 * 1024), 2) FREE_SPACE
 16               FROM DBA_FREE_SPACE
 17           GROUP BY TABLESPACE_NAME) F
 18    WHERE D.TABLESPACE_NAME = F.TABLESPACE_NAME(+)
 19   UNION ALL                                                          
 20   SELECT D.TABLESPACE_NAME,
 21          SPACE || 'M' "SUM_SPACE(M)",
 22          BLOCKS SUM_BLOCKS,
 23          USED_SPACE || 'M' "USED_SPACE(M)",
 24          ROUND (NVL (USED_SPACE, 0) / SPACE * 100, 2) || '%' "USED_RATE(%)",
 25          NVL (FREE_SPACE, 0) || 'M' "FREE_SPACE(M)"
 26     FROM (  SELECT TABLESPACE_NAME,
 27                    ROUND (SUM (BYTES) / (1024 * 1024), 2) SPACE,
 28                    SUM (BLOCKS) BLOCKS
 29               FROM DBA_TEMP_FILES
 30           GROUP BY TABLESPACE_NAME) D,
 31          (  SELECT TABLESPACE_NAME,
 32                    ROUND (SUM (BYTES_USED) / (1024 * 1024), 2) USED_SPACE,
 33                    ROUND (SUM (BYTES_FREE) / (1024 * 1024), 2) FREE_SPACE
 34               FROM V$TEMP_SPACE_HEADER
 35           GROUP BY TABLESPACE_NAME) F
 36    WHERE D.TABLESPACE_NAME = F.TABLESPACE_NAME(+)
 37   ORDER BY 1) 
 38   WHERE TABLESPACE_NAME IN ('SYSAUX','SYSTEM');


TABLESPACE_NAME   SUM_SPACE(M)   SUM_BLOCKS USED_SPACE(M)   USED_RATE(%)    FREE_SPACE(M)
----------------- -------------- ---------- --------------- --------------- ---------------
SYSAUX            22156M         2835968    21126.81M       95.35%          1029.19M
SYSTEM             8686M         1111808    8251.7M         94.99%            434.3M
可見,SYSAUX表空間已經使用了21GB左右,SYSTEM表空間已經使用了8GB左右,下面查看下使用SYSTEM和SYSAUX表空間的比較大的表有哪些。


sys@IVLDB> select * from (
  2  select segment_name,sum(bytes)/1024/1024 total_mb,tablespace_name from dba_segments where tablespace_name in
('SYSTEM','SYSAUX') group by segment_name,tablespace_name order by 2 desc)
  3  where rownum <=20;
 
SEGMENT_NAME                                        TOTAL_MB     TABLESPACE_NAME
-------------------------------------------------   ----------   --------------
AUD$                                                6680         SYSTEM
WRH$_ACTIVE_SESSION_HISTORY                         5248.0625    SYSAUX
WRH$_EVENT_HISTOGRAM_PK                             2499.0625    SYSAUX
WRH$_EVENT_HISTOGRAM                                1794.0625    SYSAUX
WRH$_LATCH_MISSES_SUMMARY_PK                        905.0625     SYSAUX
WRH$_SQLSTAT                                        816.0625     SYSAUX
WRH$_LATCH                                          800.0625     SYSAUX
C_OBJ#_INTCOL#                                      768          SYSTEM
WRH$_LATCH_MISSES_SUMMARY                           760.0625     SYSAUX
WRH$_ACTIVE_SESSION_HISTORY_PK                      712.0625     SYSAUX
WRH$_SYSSTAT_PK                                     672.0625     SYSAUX
WRH$_LATCH_PK                                       560.0625     SYSAUX
WRH$_SYSSTAT                                        504.0625     SYSAUX
I_WRI$_OPTSTAT_H_OBJ#_ICOL#_ST                      456          SYSAUX
WRH$_PARAMETER_PK                                   454.0625     SYSAUX
WRH$_SEG_STAT                                       408.0625     SYSAUX
WRH$_PARAMETER                                      384.0625     SYSAUX
WRH$_SYSTEM_EVENT                                   368.0625     SYSAUX
WRI$_OPTSTAT_HISTGRM_HISTORY                        312          SYSAUX
I_H_OBJ#_COL#                                       312          SYSTEM


可見,大表大部分都是AUD$和WRH$開頭的AWR基表,AUD$使用SYSTEM表空間,AWR的基表使用SYSAUX表空間,下面再查看下SYSAUX表空間的使用情況,可以通過v$sysaux_occupants視圖查詢到。
sys@IVLDB> SELECT occupant_name "Item", 
  2         space_usage_kbytes / 1048576 "Space Used (GB)", 
  3         schema_name "Schema", 
  4         move_procedure "Move Procedure" 
  5    FROM v$sysaux_occupants 
  6  ORDER BY 1 ;


Item                           Space Used (GB) Schema               Move Procedure
------------------------------ --------------- -------------------- -----------------------------------
AO                                  .038391113 SYS                  DBMS_AW.MOVE_AWMETA
AUDIT_TABLES                                 0 SYS                  DBMS_AUDIT_MGMT.move_dbaudit_tables
AUTO_TASK                           .000366211 SYS
EM                                           0 SYSMAN               emd_maintenance.move_em_tblspc
EM_MONITORING_USER                  .001708984 DBSNMP
EXPRESSION_FILTER                   .003540039 EXFSYS
JOB_SCHEDULER                       .010498047 SYS
LOGMNR                              .013061523 SYSTEM               SYS.DBMS_LOGMNR_D.SET_TABLESPACE
LOGSTDBY                            .001342773 SYSTEM               SYS.DBMS_LOGSTDBY.SET_TABLESPACE
ORDIM                               .000427246 ORDSYS               ordsys.ord_admin.move_ordim_tblspc
ORDIM/ORDDATA                       .013244629 ORDDATA              ordsys.ord_admin.move_ordim_tblspc
ORDIM/ORDPLUGINS                             0 ORDPLUGINS           ordsys.ord_admin.move_ordim_tblspc
ORDIM/SI_INFORMTN_SCHEMA                     0 SI_INFORMTN_SCHEMA   ordsys.ord_admin.move_ordim_tblspc
PL/SCOPE                            .001525879 SYS
SDO                                 .064758301 MDSYS                MDSYS.MOVE_SDO
SM/ADVISOR                          .199707031 SYS
SM/AWR                              18.8637695 SYS
SM/OPTSTAT                          1.14306641 SYS
SM/OTHER                            .012268066 SYS
SMON_SCN_TIME                       .008178711 SYS
SQL_MANAGEMENT_BASE                 .001647949 SYS
STATSPACK                                    0 PERFSTAT
STREAMS                             .000976563 SYS
TEXT                                .003540039 CTXSYS               DRI_MOVE_CTXSYS
TSM                                          0 TSMSYS
ULTRASEARCH                                  0 WKSYS                MOVE_WK
ULTRASEARCH_DEMO_USER                        0 WK_TEST              MOVE_WK
WM                                  .003417969 WMSYS                DBMS_WM.move_proc
XDB                                 .123962402 XDB                  XDB.DBMS_XDB.MOVEXDB_TABLESPACE
XSAMD                               .005004883 OLAPSYS              DBMS_AMD.Move_OLAP_Catalog
XSOQHIST                            .038391113 SYS                  DBMS_XSOQ.OlapiMoveProc


31 rows selected.




可見SM/AWR組件就使用了將近19GB的SYSAUX表空間,也就是說審計和AWR占用了大量的SYSTEM和SYSAUX表空間,而這些數據是可以定期清理的,都沒有必要保留太長的時間。
下面先清理審計的數據,如果要保留部分AUD$里面記錄的審計數據,可以把想要的數據插入到一張臨時表,然后直接truncate這張表就可以了,truncate操作會直接回收AUD$占用的空間。


sys@IVLDB> truncate table AUD$;
Table truncated.
sys@IVLDB> select bytes/1024/1024 from dba_segments where segment_name='AUD$';
BYTES/1024/1024
---------------
              5
可見,truncate這張表之后,6680M的空間直接降為5M,釋放了大量的SYSTEM表空間的空間。下面再來回收下SYSAUX表空間,這個相對比較麻煩,也比較耗時。
如上文所示,通過查看v$sysaux_occupants視圖,可以確定占用SYSAUX表空間過多的大部分都是AWR的基表,這樣只要刪除部分AWR數據理論上就可以回收一部分SYSAUX表空間,通常AWR的數據都會設置保留期限,10g版本默認保留7天,11g版本默認保留8天,可以通過dba_hist_wr_control視圖來查看(注:並不是所有DBA開頭的表都是數據字典,也有很多是視圖,dba_hist_wr_control就是視圖)。
sys@IVLDB> select * from dba_hist_wr_control;
      DBID   SNAP_INTERVAL         RETENTION            TOPNSQL
----------   -------------------   -------------------   ----------
1357933872   +00000 01:00:00.0     +00008 00:00:00.0     DEFAULT




大家可能會有疑問了,AWR的數據既然只保留七八天,為什么還會占用這么多的SYSAUX表空間呢?這個問題我個人認為主要有以下兩個原因,首先,AWR刪除過期的數據是通過DELETE操作完成的,這樣就會產生大量的碎片,特別是SYSAUX表空間存在自動擴展的數據文件,而且這個數據文件沒有擴展到最大,還有擴展的空間情況下會很明顯,其次就是ASH的數據有些情況下是不受AWR的保留策略影響的,這個從下面的SQL就可以看出。
sys@IVLDB> select count(*) from  WRH$_ACTIVE_SESSION_HISTORY;
  COUNT(*)
----------
  16918966
sys@IVLDB> select min(snap_id),max(snap_id) from  wrh$_active_session_history;
MIN(SNAP_ID)   MAX(SNAP_ID)
------------   ------------
           1        15533
可以看到,ASH的數據從第一個快照開始一直都在保留,導致WRH$_ACTIVE_SESSION_HISTORY表很大,使用DBMS_WORKLOAD_REPOSITORY包清理過期或者不需要的AWR數據,可以回收這部分空間。
sys@IVLDB> exec DBMS_WORKLOAD_REPOSITORY.DROP_SNAPSHOT_RANGE (low_snap_id =>1,high_snap_id => 15500);
PL/SQL procedure successfully completed.
清理了AWR數據之后,你會發現SYSAUX表空間的空間並沒有被回收,使用率還和之前一樣,這是因為清理AWR操作是通過DELETE操作實現的,表的水位線並沒有下降導致的。
sys@IVLDB> SELECT occupant_name "Item",
  2         space_usage_kbytes / 1048576 "Space Used (GB)",
  3         schema_name "Schema",
  4         move_procedure "Move Procedure"
  5    FROM v$sysaux_occupants
  6    where occupant_name='SM/AWR';
Item             Space Used (GB)   Schema               Move Procedure
--------------   ---------------   -------------------- ------------------
SM/AWR           18.8638306        SYS
AWR的數據還是使用將近19GB的空間,查詢SYSTEM和SYSAUX表空間的使用率會發現SYSTEM表空間的使用率已經降低了很多,因為上文TRUNCATE了AUD$表,這張表使用的是SYSTEM表空間,上文刪除了很多AWR的數據,AWR的數據使用SYSAUX表空間,並沒有回收。
sys@IVLDB> SELECT * FROM ( 
  2  SELECT D.TABLESPACE_NAME, 
  3          SPACE || 'M' "SUM_SPACE(M)", 
  4          BLOCKS "SUM_BLOCKS", 
  5          SPACE - NVL (FREE_SPACE, 0) || 'M' "USED_SPACE(M)", 
  6          ROUND ( (1 - NVL (FREE_SPACE, 0) / SPACE) * 100, 2) || '%' 
  7             "USED_RATE(%)", 
  8          FREE_SPACE || 'M' "FREE_SPACE(M)" 
  9     FROM (  SELECT TABLESPACE_NAME, 
 10                    ROUND (SUM (BYTES) / (1024 * 1024), 2) SPACE, 
 11                    SUM (BLOCKS) BLOCKS 
 12               FROM DBA_DATA_FILES 
 13           GROUP BY TABLESPACE_NAME) D, 
 14          (  SELECT TABLESPACE_NAME, 
 15                    ROUND (SUM (BYTES) / (1024 * 1024), 2) FREE_SPACE 
 16               FROM DBA_FREE_SPACE 
 17           GROUP BY TABLESPACE_NAME) F 
 18    WHERE D.TABLESPACE_NAME = F.TABLESPACE_NAME(+) 
 19   UNION ALL                                                           
 20   SELECT D.TABLESPACE_NAME, 
 21          SPACE || 'M' "SUM_SPACE(M)", 
 22          BLOCKS SUM_BLOCKS, 
 23          USED_SPACE || 'M' "USED_SPACE(M)", 
 24          ROUND (NVL (USED_SPACE, 0) / SPACE * 100, 2) || '%' "USED_RATE(%)", 
 25          NVL (FREE_SPACE, 0) || 'M' "FREE_SPACE(M)" 
 26     FROM (  SELECT TABLESPACE_NAME, 
 27                    ROUND (SUM (BYTES) / (1024 * 1024), 2) SPACE, 
 28                    SUM (BLOCKS) BLOCKS 
 29               FROM DBA_TEMP_FILES 
 30           GROUP BY TABLESPACE_NAME) D, 
 31          (  SELECT TABLESPACE_NAME, 
 32                    ROUND (SUM (BYTES_USED) / (1024 * 1024), 2) USED_SPACE, 
 33                    ROUND (SUM (BYTES_FREE) / (1024 * 1024), 2) FREE_SPACE 
 34               FROM V$TEMP_SPACE_HEADER 
 35           GROUP BY TABLESPACE_NAME) F 
 36    WHERE D.TABLESPACE_NAME = F.TABLESPACE_NAME(+) 
 37   ORDER BY 1)  
 38   WHERE TABLESPACE_NAME IN ('SYSAUX','SYSTEM'); 


TABLESPACE_NAME      SUM_SPACE(M)    SUM_BLOCKS USED_SPACE(M)   USED_RATE(%)  FREE_SPACE(M)
-------------------- --------------- ---------- --------------- ------------- --------------
SYSAUX               22156M             2835968 21126.81M       95.35%        1029.19M
SYSTEM               8686M              1111808 1990.25M        22.91%        6695.75M




查詢WRH$_ACTIVE_SESSION_HISTORY表會發現數據已經被刪除了很多,從刪除之前的16918966條記錄變為刪除后的4706條記錄,但是表的大小沒變,還是5GB多。
sys@IVLDB> select count(*) from WRH$_ACTIVE_SESSION_HISTORY;
  COUNT(*)
----------
      4706
下面通過MOVE操作回收這個表的水位線,來回收這部分被刪除數據占用的空間。這個表是分區表,分區表不支持表級別的MOVE操作,直接對分區表進行MOVE操作會遇到ORA-14511錯誤。
sys@IVLDB> alter table WRH$_ACTIVE_SESSION_HISTORY move;
alter table WRH$_ACTIVE_SESSION_HISTORY move
            *
ERROR at line 1:
ORA-14511: cannot perform operation on a partitioned object
查看這個表的分區信息,只有兩個分區。
sys@IVLDB>  select segment_name,partition_name,bytes/1024/1024/1024 gb from dba_segments where segment_name='WRH$_ACTIVE_SESSION_HISTORY';
SEGMENT_NAME                   PARTITION_NAME                         GB
------------------------------ ------------------------------ ----------
WRH$_ACTIVE_SESSION_HISTORY    WRH$_ACTIVE_1357933872_0            5.125
WRH$_ACTIVE_SESSION_HISTORY    WRH$_ACTIVE_SES_MXDB_MXSN      .000061035


下面按照分區進行MOVE操作,來回收空間。
sys@IVLDB> alter table WRH$_ACTIVE_SESSION_HISTORY move partition WRH$_ACTIVE_1357933872_0;
Table altered.
sys@IVLDB> alter table WRH$_ACTIVE_SESSION_HISTORY move partition WRH$_ACTIVE_SES_MXDB_MXSN;
Table altered.
對分區表進行MOVE之后,需要重建索引,查看這個表的索引信息。
sys@IVLDB> select index_name from dba_indexes where table_name='WRH$_ACTIVE_SESSION_HISTORY';
INDEX_NAME
------------------------------
WRH$_ACTIVE_SESSION_HISTORY_PK


這個表只有一個主鍵,而且是分區索引,也不能對分區索引直接進行REBUILD操作,否則會遇到ORA-14086錯誤。
sys@IVLDB> alter index WRH$_ACTIVE_SESSION_HISTORY_PK rebuild;
alter index WRH$_ACTIVE_SESSION_HISTORY_PK rebuild
            *
ERROR at line 1:
ORA-14086: a partitioned index may not be rebuilt as a whole




下面查看下這個索引的分區信息。
sys@IVLDB> select partition_name from dba_ind_partitions where index_name='WRH$_ACTIVE_SESSION_HISTORY_PK';
PARTITION_NAME
------------------------------
WRH$_ACTIVE_1357933872_0
WRH$_ACTIVE_SES_MXDB_MXSN
然后按照分區進行重建索引。
sys@IVLDB> alter index WRH$_ACTIVE_SESSION_HISTORY_PK rebuild partition WRH$_ACTIVE_1357933872_0;
Index altered.
sys@IVLDB> alter index WRH$_ACTIVE_SESSION_HISTORY_PK rebuild partition WRH$_ACTIVE_SES_MXDB_MXSN;
Index altered.
再次查看,WRH$_ACTIVE_SESSION_HISTORY的空間已經回收。
sys@IVLDB> select sum(bytes)/1024/1024 from dba_segments where segment_name='WRH$_ACTIVE_SESSION_HISTORY';
SUM(BYTES)/1024/1024
--------------------
              2.0625
sys@IVLDB> select sum(bytes)/1024/1024 from dba_segments where segment_name='WRH$_ACTIVE_SESSION_HISTORY_PK';
SUM(BYTES)/1024/1024
--------------------
               .3125
可見,這個表大小由之前的5248.0625MB將為2.0625MB,重建索引后,索引的大小也由之前的712.0625MB降為了0.3125MB,這一張表就回收了6GB左右的空間。
sys@IVLDB> SELECT occupant_name "Item",
  2         space_usage_kbytes / 1048576 "Space Used (GB)",
  3         schema_name "Schema",
  4         move_procedure "Move Procedure"
  5    FROM v$sysaux_occupants
  6    where occupant_name='SM/AWR';
Item             Space Used (GB)   Schema               Move Procedure
--------------   ---------------   -------------------- ------------------
SM/AWR           13.0436401        SYS




通過v$sysaux_occupants視圖,可以查詢到AWR占用空間由之前的將近19GB降為了不到13GB。按照同樣的方法,回收下WRH$_EVENT_HISTOGRAM表的空間,這也是分區表表1794MB,只有一個索引(是主鍵)2499MB。
sys@IVLDB> select partition_name from dba_tab_partitions where table_name='WRH$_EVENT_HISTOGRAM';
 
PARTITION_NAME
------------------------------
WRH$_EVENT_HISTO_MXDB_MXSN
WRH$_EVENT__1357933872_0
sys@IVLDB> alter table WRH$_EVENT_HISTOGRAM move partition WRH$_EVENT_HISTO_MXDB_MXSN;
Table altered.
sys@IVLDB> alter table WRH$_EVENT_HISTOGRAM move partition WRH$_EVENT__1357933872_0;
Table altered.
sys@IVLDB> select index_name from dba_indexes where table_name='WRH$_EVENT_HISTOGRAM';
INDEX_NAME
------------------------------
WRH$_EVENT_HISTOGRAM_PK
sys@IVLDB> select partition_name from dba_ind_partitions where index_name='WRH$_EVENT_HISTOGRAM_PK';
PARTITION_NAME
------------------------------
WRH$_EVENT_HISTO_MXDB_MXSN
WRH$_EVENT__1357933872_0
sys@IVLDB> alter index WRH$_EVENT_HISTOGRAM_PK rebuild partition WRH$_EVENT_HISTO_MXDB_MXSN;
Index altered.
sys@IVLDB> alter index WRH$_EVENT_HISTOGRAM_PK rebuild partition WRH$_EVENT__1357933872_0;
Index altered.




清理WRH$_ACTIVE_SESSION_HISTORY和WRH$_EVENT_HISTOGRAM兩張表,SYSAUX表空間就釋放出10GB的空間,其他占用SYSAUX空間比較大的表也可以安裝這樣的方法去釋放空間,這里就不一一演示了。
可能有人會問了,既然已經刪除了數據,那么如果不回收這部分空間,ORACLE就不會再使用這部分空間了嗎?為什么非要回收呢?這個高水位線的問題主要影響以下幾個方面,不只是使用SYSAUX表空間的表,對所有碎片較多的表都適用。
1.影響查詢速度,因為這樣的表本身比較大,索引也會很大,查詢會很慢。
2.消耗資源,因為表和索引都很大,查詢時會消耗很多I/O資源。
3.空間占用,雖然大部分數據被DELETE掉了,但是這部分空間仍舊是這個段(SEGMENT)的區(EXTENT),即使可以再利用也只能是這個表的新增數據才可以使用,而且還得是所在表空間無法自動擴展或者沒有足夠的擴展空間的情況下,如果表空間可以自動擴展或者有足夠的擴展空間,那么還是不會使用這部分空間的,這就導致表和索引會越來越大,占用的空間越來越大,而一旦將可擴展的空間用盡,那么其他表將無法擴展,DELETE掉的數據空間,其他對象是無法使用的。
除了AWR的保留策略會影響SYSAUX表空間的使用率外,AWR收集數據的級別也對SYSAUX表空間的使用率影響很大,AWR收集數據的級別由statistics_level參數控制,這個參數有三個值,BASIC、TYPICAL、ALL,BASIC表示關閉統計信息收集,TYPICAL表示普通收集級別,只收集夠日常用的統計信息,ALL是最給力的,凡是ORACLE能收集的所有信息都要收集,所以生成數據量會很大,相對來說,對性能和占用空間的影響也是最大的,通常TYPICAL就已經夠用了。
不同的版本statistics_level參數的默認值不同,有的版本默認值為ALL,有的版本默認值為TYPICAL,具體哪些版本使用ALL為默認值,我記不清了,如果您的數據庫設置statistics_level參數的值為ALL,建議調整為TYPICAL。
sys@IVLDB> show parameter statistics_level
NAME                                 TYPE        VALUE
------------------------------------ ----------- ---------
statistics_level                     string      TYPICAL
如果您的數據庫也遇到了SYSAUX表空間很大的情況,建議在清理AWR數據時,回收這部分空間,對SYSAUX表空間的對象操作,基本不會影響數據庫的正常使用,SYSAUX表空間存放的對象都是數據庫運行非必須的對象,技術這個表空間損壞或者丟失,數據庫一樣可以正常運行。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM