海量資料遷移之透過shell估算資料量

dbhelper發表於2014-11-26
在資料遷移的時候,需要根據使用者量來評估需要在表空間理新增的空間大小。比如遷移5百萬的使用者和遷移200萬,兩者需要新增的資料量差別很大,在資源有限的情況下,需要一些比較合理的估算,畢竟在生產環境中做資料載入的時候報了空間不足的問題就是準備太不充分了,稍後的資料修復任務就難上加難。
比如我們現在客戶提供瞭如下的資訊,需要我們評估一下在目前的使用者基礎上遷移幾百萬使用者需要新增的空間。
表空間假設是如下的儲存情況。DATA開頭的表空間存放表資料,INDX開頭的表空間存放索引資料。
Tablespace Init extent Total MB Free MB Used MB
-------------------- ---- ------------ ---------- -----------
DATAH01 16M 572,113 135,408 436,705
DATAL01 8M 216,179 141,360 74,819
DATAM01 4M 291,840 85,280 206,560
DATAS01 1M 302,080 74,508 227,572
INDXH01 4M 174,033 96,256 77,777
INDXM01 2M 141,312 56,812 84,500
INDXS01 128K 240,640 72,241 168,399
sum   1,938,197 661,865 1,276,332

現在得到的是整個資料庫的儲存情況。使用者說現在庫裡還有600G左右的空間,讓我們評估一下再遷移幾百萬的使用者的情況需要多少空間。
比如資料庫裡用到的表有1000張,可能做資料遷移的時候關聯的表只有100張。那麼我們不能按照如下的比例來做計算。
10%*total_size*新新增的使用者佔用的比率

這樣肯定是不科學的,而且估算的空間肯定是偏小的。
比如memo這一個表就80多個G,按照百分比計算就會出問題。

TABLE_NAME                        SIZE_MB TABLESPACE_NAME
------------------------------ ---------- ------------------------------
MEMO                            81613 DATAS01

而從客戶的角度出發,他們需要的結果類似下面的表格內容。
如果提供瞭如下的表格,客戶一看就一目瞭然,大概需要新增多少的空間。
INDEX_SIZE TOTAL_SIZE INDXH01 INDXM01 INDXS01  
sum 306093 62836 57302 185392  
           
           
TABLE_SIZE TOTAL_SIZE DATAH01 DATAL01 DATAM01 DATAS01
sum 546981 132944 72400 126508 215129


我採用瞭如下的兩個shell指令碼來做計算。
如下的指令碼計算存放表資料的表空間的資料量
我們假設我們有一個檔案,裡面是資料遷移中用到的表清單,取名為tablst,然後透過如下的指令碼來做計算。

awk '{print "'\''" $1 "'\''" ","}' tablst |sed -e '/^$/d' -e '$s/.$//' > tablst.temp
table_list=`cat tablst.temp`

sqlplus -s  xxxxxxx < set linesize 200
set pages 100
col table_name format a30
break on report
compute sum of total_size on report
compute sum of INDXH01 on report
compute sum of INDXM01 on report
compute sum of INDXS01 on report

 select table_name,
      sum(size_MB) total_size,
      sum(decode(tablespace_name,'INDXH01', size_MB,0)) INDXH01,
      sum(decode(tablespace_name,'INDXM01', size_MB,0)) INDXM01,
      sum(decode(tablespace_name,'INDXS01', size_MB,0)) INDXS01
     from (select idx.table_name, round(sum(seg.bytes/1024/1024)) size_MB,seg.tablespace_name from  user_segments seg,user_indexes idx where seg.segment_name=idx.index_name and  idx.table_name='MO1_MEMO' group by idx.table_name,seg.tablespace_name)
    group by table_name;

EOF
rm tablst.temp


假設我們我們計算3個表。MEMO,CHARGE,CHARGE_REL,執行指令碼後我們得到如下的清單,就很清楚的看到,哪些表佔用了多少空間,在哪個表空間。
TABLE_NAME                     TOTAL_SIZE    DATAH01    DATAL01    DATAM01    DATAS01
------------------------------ ---------- ---------- ---------- ---------- ----------
    CHARGE                         104720     104720          0          0          0
    MEMO                            81613          0          0          0      81613
CHARGE_REL                          12672      12672          0          0          0
                               ---------- ---------- ---------- ---------- ----------
sum                                199005     117392          0          0      81613

透過如下的指令碼來估算索引的表空間使用情況。

awk '{print "'\''" $1 "'\''" ","}' tablst |sed -e '/^$/d' -e '$s/.$//' > tablst.temp
table_list=`cat tablst.temp`

sqlplus -s  xxxx < set linesize 200
set pages 100
col table_name format a30
break on report
compute sum of total_size on report
compute sum of DATAH01 on report
compute sum of DATAH01 on report
compute sum of DATAL01 on report
compute sum of DATAM01 on report
compute sum of DATAS01 on report
 select table_name,
      sum(size_MB) total_size,
      sum(decode(tablespace_name,'DATAH01', size_MB,0)) DATAH01,
      sum(decode(tablespace_name,'DATAL01', size_MB,0)) DATAL01,
      sum(decode(tablespace_name,'DATAM01', size_MB,0)) DATAM01,
      sum(decode(tablespace_name,'DATAS01', size_MB,0)) DATAS01
     from (select segment_name table_name, round(sum(bytes/1024/1024)) size_MB,tablespace_name from  user_segments where segment_name in ($table_list) group by segment_name,tablespace_name)
    group by table_name;

EOF
rm tablst.temp

執行後得到的如下的一個清單,就可以看到表對應索引的儲存情況。
TABLE_NAME                     TOTAL_SIZE    INDXH01    INDXM01    INDXS01
------------------------------ ---------- ---------- ---------- ----------
    CHARGE                          27004      21620          0       5384
       CHARGE_REL                  28868      28868          0          0
    MEMO                            33999          0          0      33710
                               ---------- ---------- ---------- ----------
sum                                 89871      50488          0      39094

得到了如上的列表,需要評估資料量的情況就有思路了。
可以基於當前資料庫中的剩餘空間來排查目前的空間是否足夠,如果不夠需要新增多少。

Tablespace Init extent Total MB Free MB Used MB
-------------------- ---- ------------ ---------- -----------
DATAH01 16M 572,113 135,408 436,705
DATAL01 8M 216,179 141,360 74,819
DATAM01 4M 291,840 85,280 206,560
DATAS01 1M 302,080 74,508 227,572
INDXH01 4M 174,033 96,256 77,777
INDXM01 2M 141,312 56,812 84,500
INDXS01 128K 240,640 72,241 168,399
sum   1,938,197 661,865 1,276,332

得到一個基本的清單,我們就需要加入一定的buffer空間,個人覺得控制在30%左右比較好。這樣留有一定富餘。
最後給客戶的建議就是如下的清單,客戶一看就一目瞭然。

INDXM01 +50G

INDXS01 +100G

DATAM01 +50G

DATAS01 +100G


    

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

相關文章