Oracle – Shrinking/Reclaiming Free Tablespace Space

oracleoracle-12cshrinktablespaces

I have a Oracle 12c tablespace with the size of 90GB. Almost 40GB are free.

TB1 54 %    90880   41383   49497   46  98304   50 %    ONLINE  PERMANENT

The tablespace has 3 datafiles.

E:\ORACLE\ORADATA\xx\TB1.DBF    33554416    True    100 
F:\ORACLE\ORADATA\xx\TB1_2.DBF  33554416    True    100 
G:\ORACLE\ORADATA\xx\TB1_3.DBF  25344000    True    100

How can I shrink the tablespace to reclaim the free 40GB (datafiles on disk)? I can not have a downtime.

Best Answer

I agree with EdStevens' comment, but here are some other ideas:

The AskTom website has a script that will list exactly how much you can shrink the existing data files.

If that doesn't yield much savings, you can find the biggest indexes on that tablespace and rebuild them; that is a temporary solution and the indexes would eventually get big again, but if budget doesn't allow more disk space now, try this query:

select segment_name, sum(bytes)/1024/1024 as mb 
from dba_segments 
where tablespace_name='TB1' and segment_type like 'INDEX%'
group by segment_name
order by mb;

Then if you find an index named ind_big_stuff is huge, then

alter index ind_big_stuff rebuild online;

Also, if your application is a commercial application, there may be several tables with zero rows. Or if you have partitioned tables, you may have some partitions with zero rows. You can drop space allocated to them with

exec dbms_space_admin.drop_empty_segments(schema_name=>'HR');

You can use the segment creation deferred clause on an alter table statement for things like partitioned tables, or tables you know will not have any rows.