巧用flashback database實現靈活的資料切換
客戶今天有一個需求,因為開發現在在生產環境中遇到了一些困難,需要在測試生產環境中複現問題,這樣就需要從生產環境抽取出一些資料,可能資料量相對比較小,有個1G左右。需要把這些資料載入到測試生產環境中,還是來張圖更加清晰。我們需要把圖中右邊部分的生產環境中抽取部分資料匯入到測試生產環境中,這裡所說的測試生產環境是按照生產環境的結構來複製的。測試環境已經有一些測試資料,很可能和生產環境中的資料衝突。
就如同圖中下面的部分列出的細節一樣,很可能會存在資料衝突導致資料載入出現問題。
按照一般的情況下,我們是建議對測試生產環境做一個備份,採用expdp即可,然後清空對應schema下的資料,然後倒入需要重現問題的資料。問題複現之後,可以使用備份把資料恢複回來。
但是這種固有的思想還是存在一定的問題。
客戶回函的情況如下,說對應的schema下的資料量是相當大的,差不多2T多,如果做備份也是需要不少的空間,匯出匯入都是相當消耗時間和資源的。
OWNER SUM(BYTES)/1024/1024
------------------------------ --------------------
APPO 2144666.63
這套環境借用的時間為3天,所以相對來說測試環境的高可用要求就沒那麼高了。
我們可以嘗試採用flashback database來完成這種需求。
使用flashback database會有一些的顧慮和隱患,比如閃回時間的考慮,如果考慮不周很可能達不到預期的效果。
資料庫中預設是不會啟用閃回資料庫功能的,需要啟用,完成資料恢複之後,再禁用,這些過程都是需要停庫啟庫的,對於中介軟體來說就需要重新啟動,需要和開發測試部分做協調,是否同意這種方式。
資料庫做閃回操作之後,閃回到了資料清除前的狀態,這個時候如果要開啟資料庫,是需要使用open resetlogs這種方式的,這樣的話這個時間點之前的備份就失效了。也需要做確認,確保不會出現業務上意料之外的情況。
很快得到了回複,看來對於這種方式大家也是認可的,畢竟能夠免去大量的備份和資料匯入匯出之苦。操作上也相對比較方便。
我們使用下面的指令碼來簡單類比一下。我們建立一個表,然後啟用flashback database功能,做truncate操作,然後匯入一些新的資料,之後再做閃回資料庫操作,閃回到truncate之前的資料情況,最後啟用資料庫即可。
修改閃回保留的時間,預設是1440分鐘,即24小時
SQL> show parameter flashback
NAME TYPE VALUE
------------------------------------ ----------- ------------------------------
db_flashback_retention_target integer 1440
我們建立了一個表,大小為2G左右,這樣能夠簡單驗證一下閃回日誌的增長情況。
SQL> select segment_name,bytes from user_segments where segment_name='AA';
SEGMENT_NAME BYTES
--------------- ----------
AA 2153775104
SQL> SELECT COUNT(*)FROM AA;
COUNT(*)
----------
18340352
我們開始啟用閃回資料庫功能。
SQL> shutdown immediate
Database closed.
Database dismounted.
Oracle instance shut down.
SQL> startup mount
ORACLE instance started.
Total System Global Area 435224576 bytes
Fixed Size 1337044 bytes
Variable Size 272632108 bytes
Database Buffers 155189248 bytes
Redo Buffers 6066176 bytes
Database mounted.
SQL> alter database flashback on;
Database altered.
SQL>
SQL> alter database open;
Database altered.
啟用之後,得到一個時間戳記,一次來作為我們完成閃回的時間點。
select systimestamp from dual;
接著我們來做一個清理工作。
SQL> truncate table aa;
Table truncated.
我們嘗試插入一部分
SQL> insert into aa select*from all_objects;
71642 rows created.
SQL> commit;
Commit complete.
這個資料量相比原本的2G就小了很多。
然後我們嘗試使用閃回資料庫功能,閃回到刪除之前的狀態。
SQL> shutdown immediate
Database closed.
Database dismounted.
ORACLE instance shut down
SQL> startup mount;
ORACLE instance started.
Total System Global Area 435224576 bytes
Fixed Size 1337044 bytes
Variable Size 272632108 bytes
Database Buffers 155189248 bytes
Redo Buffers 6066176 bytes
Database mounted.
SQL> Flashback database to timestamp to_timestamp('2015-04-17 17:42:29','yyyy-mm-dd hh24:mi:ss');
Flashback complete.
以唯讀方式開啟,做驗證,保證閃回沒有問題。
SQL> alter database open read only;
Database altered.
SQL> conn n1/n1
Connected.
SQL> select count(*)from aa;
COUNT(*)
----------
18340352
資料又回來了。
查看閃回日誌的大小,可以看到還是很少的。
total 16040
-rw-r----- 1 ora11g dba 8200192 Apr 17 17:43 o1_mf_bm1oc2qt_.flb
-rw-r----- 1 ora11g dba 8200192 Apr 17 17:45 o1_mf_bm1ofwb7_.flb
[ora11g@oel1 flashback]$ pwd
/u02/ora11g/flash_recovery_area/TEST11G/flashback
[ora11g@oel1 flashback]$
另外說明一下,對於閃回資料庫功能,如果禁用之後,閃回日誌會自動清除。
Oracle 11g flashback Data Archive(閃回資料歸檔)
Oracle flashback閃回機制
flashback table快速恢複誤刪除的資料
Oracle 備份恢複:flashback閃回
[Oracle]閃回flashback功能的使用