昨天的事情,同事讓我刪除某條數據,我使用了上下鍵,沒有注意那張表,直接把後面的條件刪掉,加上分號,回車了。。。。啊。。。。
幸虧數據不是很多,有備份數據,但是那樣回覆太慢了。另闢蹊蹺,這個也是跟別人學得。下面開始。。
先把binlog考到一個臨時的目錄,如果沒有記錄操作前的pos,只能手動找了,說個笨方法,根據執行的命令查看一下這條命令的位置
mysqlbinlog -vv --base64-output=DECODE-ROWS binlog-mysql-7.000007 | grep -n "DELETE FROM `test`.`tt`"
179298:### DELETE FROM `test`.`tt`
然後看好以下這個位置前面的若干行;
DELIMITER /*!*/;
# at 4
#140520 14:03:53 server id 1 end_log_pos 106 Start: binlog v 4, server v 5.1.73-log created 140520 14:03:53 at startup
# Warning: this binlog is either in use or was not closed properly.
ROLLBACK/*!*/;
BINLOG '
SfB6Uw8BAAAAZgAAAGoAAAABAAQANS4xLjczLWxvZwAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA
AAAAAAAAAAAAAAAAAABJ8HpTEzgNAAgAEgAEBAQEEgAAUwAEGggAAAAICAgC
'/*!*/;
# at 1553209
# at 1553259
# at 1554274
# at 1555289
# at 1556304
# at 1557319
就是這個位置。pos=1559972
或者直接用前面的那個179298 ,直接
mysqlbinlog -vv binlog-mysql-7.000007 | sed -n '217175,$p'
這裏還需要注意的是,這個文件結尾是不是自己需要的,因爲數據庫在你cp的時候很有可能還會寫數據。。。
mysqlbinlog -vv --base64-output=DECODE-ROWS binlog-mysql-7.000007 | sed -n '179298,$p'| sed 's/^### //g;s/^#.*//g;s/COMMIT.*//g;s/DELIMITER.*//g;s/ROLLBACK.*//g;s#/.*[/;]$##g'
這個就是把那些和SQL語句不想管的全部都替換掉。
DELETE FROM `test`.`tt`
WHERE
@1=221
@2=222
@3='BZ001117'
@4=0
@5=NULL
@6=0
@7=0
@8=NULL
類似於這樣的SQL了。接下來你該知道怎麼做了吧。
接着上面那條命令繼續
後面就是把這個SQL換成insert into。
mysqlbinlog -vv --base64-output=DECODE-ROWS binlog-mysql-7.000007 | sed -n '179298,$p'| sed 's/^### //g;s/^#.*//g;s/COMMIT.*//g;s/DELIMITER.*//g;s/ROLLBACK.*//g;s#/.*[/;]$##g;s/`//g;s/DELETE FROM/INSERT INTO /g;s/WHERE/VALUES /g;s/\(VALUES\)/\1(/g;s/\(@[1-7]=\)\(.*\)/\2,/g;s/\(@.=\)\(.*\)/\2);/g' >2.sql
結果是這樣子,
INSERT INTO test.tt
VALUES(
221 ,
222 ,
'BZ001117' ,
0 ,
NULL ,
0 ,
0 ,
NULL );
好像可以了,那就試試
mysql> select count(*) from tt;
+----------+
| count(*) |
+----------+
| 221 |
+----------+
1 row in set (0.00 sec)
果然OK
解決問題了,最後說的是,任何操作頭腦要清楚,不要盲目,看清楚在執行。
這個我感覺是最快的恢復誤刪除的方法。