尝试删除AWR导入的SNAPSHOT,发现快照并没有被彻底删除。
在10.2.0.3环境下执行的DBMS_WORKLOAD_REPOSITORY.DROP_SNAPSHOT_RANGE过程,Oracle很快就返回了结果,感觉似乎Oracle并没有真正进行删除,因为这部分快照的导入用了将近一个小时:
SQL> select * from v$version;
BANNER
----------------------------------------------------------------
Oracle Database10gEnterpriseEdition Release10.2.0.3.0 - 64bi
PL/SQL Release 10.2.0.3.0 - Production
CORE 10.2.0.3.0 Production
TNS for Linux: Version 10.2.0.3.0 - Production
NLSRTL Version 10.2.0.3.0 - Production
SQL> select min(snap_id), max(snap_id)
2 from dba_hist_snapshot
3 where dbid = 3944144691;
MIN(SNAP_ID) MAX(SNAP_ID)
------------ ------------
45189 47802
SQL> exec dbms_workload_repository.drop_snapshot_range(45189, 47802, 3944144691)
PL/SQL procedure successfully completed.
SQL> select * from dba_hist_snapshot where dbid = 3944144691;
no rows selected
如果检查数据字典可以发现,Oracle仅仅修改了对应SNAPSHOT的状态,而并没有删除快照:
SQL> select dbid, status, count(*)
2 from wrm$_snapshot
3 group by dbid, status;
DBID STATUS COUNT(*)
---------- ---------- ----------
3812548755 0 89
96312462 0 50
3944144691 2 2614
查询metalink发现是Oracle的bug,Bug 8622802描述了这个问题,确认影响的版本包括10.2.0.3、10.2.0.4。Oracle在版本12、11.2.0.2以及10.2.0.5中修正了这个问题。
测试发现11.2中同样存在这个问题:
SQL> select * from v$version;
BANNER
--------------------------------------------------------------------------------
Oracle Database11gEnterprise Edition Release11.2.0.1.0 - 64bit Production
PL/SQL Release 11.2.0.1.0 - Production
CORE 11.2.0.1.0 Production
TNS for Linux: Version 11.2.0.1.0 - Production
NLSRTL Version 11.2.0.1.0 - Production
SQL> select min(snap_id), max(snap_id)
2 from dba_hist_snapshot
3 where dbid = 3944144691;
MIN(SNAP_ID) MAX(SNAP_ID)
------------ ------------
45189 47802
SQL> exec dbms_workload_repository.drop_snapshot_range(45189, 47802, 3944144691)
PL/SQL过程已成功完成。
SQL> select dbid, status, count(*)
2 from wrm$_snapshot
3 group by dbid, status;
DBID STATUS COUNT(*)
---------- ---------- ----------
4284478783 0 197
3944144691 2 2614
对于这个错误导致的一个比较严重的影响就是占用空间没有释放,如果和当前例子一样,打算删除指定数据库的所有快照,可以使用下面的过程:
SQL> select dbid, status, count(*)
2 from wrm$_snapshot
3 group by dbid, status;
DBID STATUS COUNT(*)
---------- ---------- ----------
3812548755 0 94
96312462 0 50
3944144691 2 2614
SQL> exec dbms_swrf_internal.unregister_database(3944144691)
PL/SQL procedure successfully completed.
SQL> select dbid, status, count(*)
2 from wrm$_snapshot
3 group by dbid, status;
DBID STATUS COUNT(*)
---------- ---------- ----------
3812548755 0 94
96312462 0 50