記一次業務人員誤刪資料後的處理方法

資料和雲發表於2020-03-30

原文連結:  


摘要:一次業務人員刪除資料後,恢復的思路,供參考,有問題歡迎指出

記錄一次意外刪除業務表資料的處理
在一個週六的中午,突然接到了客戶的電話,說有一個很緊急的故障需要處理,開發人員誤刪了一張業務表,且因為種種原因已經commit,現在需要恢復。雖然後來才知道是非常核心的業務表(以下稱表A),當天這個操作已經嚴重影響電信使用者查詢修改各種套餐,不過當時並沒有想到影響這麼大,後續的處理過程也讓給我一個深刻的教訓。
由於以前也經歷過類似的事件,當時的時間約是10點10分左右,客戶和我說操作時間在9點50分左右,時間不算常,第一時間想起用undo閃回查詢保留資料:
select * from table_name as of timestamp to_timestamp(‘2019-xx-xx xx:xx:xx’,‘YYYY-MM-DD HH24:MI:SS’);
10點15查詢當前A表的才200多條,查9點55 229條,查9點53分就160多萬行,不過數量級還是不對,客戶說正常應該1200萬左右,再閃回查詢,這期間可以看到隨著時間往前推移行數在不斷增加:10點51的980萬,10點50的時候就變1500萬,9點49的時候有 2300萬,9點48分10秒的時候有3000萬,9點48分0秒就報快照過久了。不過我發現9點48分08秒到9點48分10秒這段時間內行數沒有減少,行數在3000萬左右;介於剛才的查詢每一秒行數都在減少的情況下,我主觀認為這個時刻可能就是delete之前行數最大的時刻,和客戶溝通這個行數也和業務對得上,48分0秒undo就過期了,當時覺得有點幸運,抓緊create table as select 建立出備份表,資料出來了後續就讓開發人員折騰資料就行了,以為這事結了,準備吃口飯時,客戶打來電話,說資料還是不對,還是少。不過這時我也沒太慌,因為在設計這套庫的時候就已經考慮到可能有這種delete發生,所以在上線的之前就已經開啟了資料庫的flashback,我尋思最差最差就用flashback table恢復這個表,雖然不如ctas建立備份表讓開發人員倒騰資料對原表以及業務影響小,但是也沒什麼其他好的辦法了。執行flashback table 命令,報錯,還是報快照過久。這個時候我就非常慌了,明明開了flashback了,為什麼還是報錯。抓緊問問專家,才明白咋回事:
alter database flashback on;
這條命令開啟的是資料庫級別的閃回,並不代表資料庫中的每個表隨時都能閃回,資料庫級別的閃回只能把整個資料庫閃回到某個時刻;這樣就非常棘手了,和專家和客戶商量,想出了一條解決方案:
1.停庫,起mount

2.flashback database to timestamp to_timestamp(‘2019-09-07 09:47:54’,‘yyyy-mm-dd hh24:mi:ss’);

3.alter database open read only;

4.查資料是否滿足要求,expdp匯出

5.停庫 起mount

6.recover database;
alter database open;
測試環境下簡單測試下可以操作,不過心裡非常害怕,萬一recover有問題,那不是這個表的問題了,整個資料庫都回到47分54秒,影響非常巨大,內心十分抗拒這個方案,無奈影響太大,需要儘快恢復。不過後來和客戶再三溝通該方案的風險性,再加上已經恢復了3000萬左右的資料,客戶同意採用風險度較低的異機恢復方案,這才稍微放下點心來。
異機恢復還算順利,我們從全備恢復出資料庫來,歸檔也從備份里拉出來,然後recover指定時間,一秒一秒recover,recover一秒查一次行數,最後資料量大約在3300萬左右,該故障告一段落。
我認為本次故障我的失誤佔了很大一部分,本來對flashback不是很熟悉,誤認為flashback table這個命令是依賴於flashback database on;實際上該命令完完全全是依賴於undo,和閃回查詢是一個東西,對於一個自己不熟悉的技術,絕對不能自以為是的用於生產環境,任何一個變更操作都要在做了充足的測試後才能給客戶使用,本次故障讓我受益匪淺,以後我也將銘記於心,不會再發生類似事件。
亡羊補牢,事情結束後第一時間準備開啟可以不依賴undo閃回查詢表的flashback archive技術,這個flashback archive的粒度是表,可以閃回查詢指定保留時間的資料,且不依賴undo表空間,如果想實現業務表的實時回溯,那flashback archive可以滿足要求,flashback database 實用性不高,一般用在備庫上居多,下面貼出我整理的flashback archive的簡單步驟,可以參考參考:
flashback archive 測試:
開啟flashback archive前提:
undo管理是AOTU
表空間必須是ASSM

1.建立flashback archive 表空間
create tablespace fba datafile ‘+DATADG’ size 10g;

2.建立flashback archive 區域
create flashback archive default fba1 tablespace fba retention 2 day; //建立時指定資料庫預設閃回區域

查詢:
select flashback_archive_name name, status from dba_flashback_archive;
select OWNER_NAME,FLASHBACK_ARCHIVE_NAME,FLASHBACK_ARCHIVE#,RETENTION_IN_DAYS,CREATE_TIME,LAST_PURGE_TIME,STATUS from dba_flashback_archive;

3.嘗試修改保留時間:
alter flashback archive fba1 modify retention 1 day;

4.清空flashback archive中的全部資訊:
alter flashback archive fba1 purge all;
清空1天前的資訊:
alter flashback archive fba1 purge before timestamp (systimestamp - interval ‘1’ day);

5.建立測試資料
test1 2936192 384M
test2 2936192 384M

6.把test2 放到flashback archive 裡面去
alter table test2 flashback archive fba1;
查詢:
SELECT table_name,archive_table_name,status from dba_flashback_archive_tables;

7.都delete掉 18:07 左右
delete from test1;
delete from test2; 佔用了1000m的表空間

8.做些別的操作確保清空undo

9.查詢嘗試:
test1已經無法查詢:
select count(*) from test1 as of timestamp to_timestamp(‘2019-09-18 18:01:00’,‘YYYY-MM-DD HH24:MI:SS’)
*
ERROR at line 1:
ORA-01555: snapshot too old: rollback segment number 10 with name “_SYSSMU10_1251597811$” too small

test2 可以在開啟後查詢任意時間的資料:
SQL> select /*+ parallel(16)  / count() from test2 as of timestamp to_timestamp(‘2019-09-18 18:20:00’,‘YYYY-MM-DD HH24:MI:SS’);

COUNT(*)

2936192


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

相關文章