天天看點

删庫不要跑,我站起來還可以删

原文位址: https://copyfuture.com/blogs-details/201909061555306597xvo4pefwz7sy68

删庫不要跑,學學下面的操作,每天執行一次rm -rf /*不是夢

上午删完,下午恢複,一天就過去了,還不用加班

前些日子在菜鳥架構上看到一篇伺服器誤删檔案的恢複過程文章,感覺挺有意思的,在這裡進行分享一波。

事故背景

大佬:"這裡有個在生産伺服器上安裝Oracle的任務,部門的哪個妹子接一下"

然後有個妹子接受了大佬的安裝Oracle的任務,妹子未注意到shell的文法,當變量未被指派的時候,會是個空值。注意了,圈起來要考的。

妹子執行指令如下:

rm -rf $ORACLE_BASE/*           

看到這條指令,你就知道有多危險了,更何況妹子用的是root賬号??what?

“很幸運”,ORACLE_BASE不存在或者未指派,上面指令變成大家熟悉的:

rm -rf /*           

root使用者?執行後,可以跑路了...

(插個小技巧:使用${var:=初始值},可以讓未定義的變量或者空值進行賦初值)

當然,妹子沒跑路,那個大佬也沒跑路,穩穩的背下了恢複資料的大鍋。

整個盤的檔案都被删了,咋辦~ ~

大佬的原文是:

mysql資料庫不是在運作嗎?linux能删除正在執行的檔案?反正是徹底删除了,最後還剩一個tomcat的log檔案,估計是檔案過大,一時沒有删除成功

看着妹子自責的眼神,又是因為這事是我安排她做的,也沒有跟她講清厲害關系,沒有任何教育訓練,責任隻能一個人背了,況且怎麼能讓美女背負這個責任呢? 打電話到機房,将盤挂到另一台伺服器上,ssh上去檢視檔案全部被清,這台伺服器運作的可是一個客戶的生産系統啊,已經運作大半年了,得盡快恢複啊。于是找來脫機備份的資料庫,發現備份檔案隻有1kb,裡面隻有幾行熟悉的mysqldump注釋(難道是crontab執行的備份腳本有問題),最接近的備份也是2013年12月份的了,真是屋漏偏逢連夜雨啊。想起來一位上司說過的案例:當一個生産系統挂掉以後,發現所有備份都有問題,刻錄的CD光牒也有劃痕,錄音帶機也壞了(一個業界前輩,估計以前還用CD光牒做備份了),沒想到今天真的應驗到我的身上了,怎麼辦??

部門上司知道情況後,已經做了最壞的B計劃:上司親自帶隊和産品AA周日趕到客戶所在的地市,星期一去上司層溝通;BB和CC去客戶管理者那邊想辦法說服客戶。。。

大佬接下來試了兩種方法恢複資料:

ext3grep和extundelete,都是隻能恢複一部分資料(原因:事故發生後,沒有及時發現,造成部分資料寫入磁盤,造成不可恢複問題。)

兩個工具的下載下傳位址(寄希望于工具?送四個字:聽天由命):

ext3grep:

https://code.google.com/p/ext3grep/

extundelete:

http://extundelete.sourceforge.net/

慶幸的是:

binlog檔案還在。沒看到大佬說的是恢複的binlog檔案還是說該檔案存在另外的盤,反正就是binlog檔案找到了。

那不用說,資料是沒問題了。普及下binlog檔案的認識。

binlog 基本認識

MySQL的二進制日志可以說是MySQL最重要的日志了,它記錄了所有的DDL和DML(除了資料查詢語句)語句,以事件形式記錄,還包含語句所執行的消耗的時間,MySQL的二進制日志是事務安全型的。

一般來說開啟二進制日志大概會有1%的性能損耗,這點消耗完全是可以接受的,為了資料的安全。

從binlog日志恢複資料

恢複文法格式:

mysqlbinlog mysql-bin.0000xx | mysql -u使用者名 -p密碼 資料庫名

常用選項:
  --start-position=953                   起始pos點
  --stop-position=1437                   結束pos點
  --start-datetime="2013-11-29 13:18:54" 起始時間點
  --stop-datetime="2013-11-29 13:21:53"  結束時間點
  --database=zyyshop                     指定隻恢複zyyshop資料庫(一台主機上往往有多個資料庫,隻限本地log日志)
    
不常用選項:    
  -u --user=name              Connect to the remote server as username.連接配接到遠端主機的使用者名
  -p --password[=name]        Password to connect to remote server.連接配接到遠端主機的密碼
  -h --host=name              Get the binlog from server.從遠端主機上擷取binlog日志
  --read-from-remote-server   Read binary logs from a MySQL server.從某個MySQL伺服器上讀取binlog日志           

小結:實際是将讀出的binlog日志内容,通過管道符傳遞給mysql指令。這些指令、檔案盡量寫成絕對路徑;

總結一波

說實話,錯誤挺低級的。應該比我以前寫的一篇,redis key*的那種錯誤更加低級。

先看看大佬的總結:

  • 本次安排MM進行伺服器維護時沒有提前對她進行說明厲害情況,自己也未重視,管理混亂,流程混亂。一個線上的生産系統,任何一個改動一定要先謀而後動。
  • 自動備份出現問題,沒有任何人檢查。脫機備份人員每次從伺服器上下載下傳1k的檔案卻從未重視。需要明确大家在工作崗位上的責任。
  • 事故發生後,沒有及時發現,造成部分資料寫入磁盤,造成不可恢複問題。需要編寫應用監控程式,服務一旦有異常,短信告警相關責任人。
  • 不能使用root使用者來操作。應該在伺服器上開設不同權限級别的使用者。

我也簡單的總結一下:

猜想,這個妹子應該是運維的小姐姐,不是開發人員(運維嗎?過分了呀,那我也要轉運維)

  • root使用者,一定是不能随便用來用的,而且還是生成環境,按照需要來配置設定不同權限的賬号使用
  • shell文法熟知過少?還是疏忽了,我猜應該是沒重視
  • 不過直接用變量來rm -rf來調用,其實也是有問題的,需要把變量輸出一下瞅瞅是啥值。建議是,如果是變量的路徑需要rm -rf的,先把變量輸出,再拷貝變量的值路徑,進行删除
  • 了解下binlog是必要的
  • shell指令可以再熟悉熟悉

另外,出了這麼大的事故,部門上司的做法不錯

原文:

通過本次事故,幾位跟這個項目和事故沒有任何關系的同僚,主動前來幫忙,查資料,幫測試,有一位同僚還幫忙到晚上1點多鐘進行資料恢複測試。同時産品經理在想到面向客戶的巨大壓力的情況下,沒有慌亂而責怪開發人員和具體操作人,而讓大家能靜下心來想解決方案。部門上司也積極主動的幫忙想辦法,陪我們加班測試,實時跟蹤事情程序

真不知道我線上上環境來個rm -rf /*會背多大的鍋,可能會n+1吧、

不過畢竟沒有權限~ ~(躍躍欲試的表情此刻變成了彎眉)

建議在執行 rm -rf /* 類似的指令的時候,自己檢查3遍,請小夥伴看看,有未知變量的,把變量輸出一遍,就不會出現這種情況了。

吾非大神,與汝俱進

最後插播廣告時間:公衆号未關注的貝貝們可以來一波關注

感謝關注