MySQL核心月報2014.10-MySQL· 捉蟲動態·binlog重放失敗
背景
在 MySQL 日常維護中,要回滾或者恢復資料,我們經常會用 binlog 來在資料庫上重放,執行類似下面的語句:
mysqlbinlog mysql-bin.000001 | mysql -hxxxx -Pxx -u
最近遇到了這樣一個問題,在重放 binlog 時,mysqld 報這樣的錯
ERROR 1064 (42000) at line 25: You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near `DELIMITER ;
分析
上面的錯是說語法不對,難道是 binlog 寫錯了,為了方便檢視,先把 mysqlbinlog 解析結果儲存到一個檔案
mysqlbinlog mysql-bin.000001 > abc.sql
然後開啟 abc.sql 檔案,會看到這樣的語句
“CREATE TABLE t_binlog_sbr(a int)^@”
最後面的奇怪的 “^@” 這是啥呢,我們用二進位制方式開啟檔案後,發現這個其實是1個位元組,值是 00,被顯示成 “^@”了。
為啥後面會多 1 個 0 呢,後來發現是使用者在用 MySQL C API 時用錯了,具體是這個函式 mysql_real_query,基原型是
int mysql_real_query(MYSQL *mysql, const char *stmt_str, unsigned long length)
詳細說明參考這裡,length 參數列示 stmt_str 的長度,所以正常的呼叫應該是這樣的:
mysq_real_query(mysql, sql, strlen(sql))
可是使用者在使用時多加了個1,變成這樣
mysq_real_query(mysql, sql, strlen(sql) + 1)
最終導致記錄的 binlog 後面多了個 ` `。 這個問題只在 statement 格式有,row 格式沒有。
解決方法
有同學會問,+1 可以,+2、 +3 呢,這個是不可以的,>=2 的都是不行的,語句發過來後,mysqld 在 parse_sql 階段直接報錯返回了,後面就不會執行了。
1) 修改程式碼
mysq_real_query(mysql, sql, strlen(sql) + 1) 這種用法是不對的,但是 MySQL 卻允許,雖然這麼用是不對的,但是為了相容性,最好還是允許這種使用方式,但是在寫binlog的時候做個判斷,長度是不是寫錯了,錯了的話糾正過來,在 THD::binlog_query 裡面改。
2) 5.6 版本加引數
如果是用 5.6 版本的 mysql client 的話,在重放時出錯提示資訊不一樣,是類似下面這樣的,更加友好,這個錯誤是 mysql client 報的,不是mysqld報的:
ERROR at line 24: ASCII ` ` appeared in the statement, but this is not allowed unless option –binary-mode is enabled and mysql is run in non-interactive mode. Set –binary-mode to 1 if ASCII ` ` is expected….
5.6 版本的 mysql client 多了一個引數 –binary-mode,允許語句裡有 ` `,所以如果是用5.6的話,就可以不用修改程式碼,重放binlog時這樣做就可以了:
mysqlbinlog mysql-bin.000001 | mysql –binary-mode -hxxxx -Pxx -u
相關文章
- MySQL核心月報2015.03-MySQL·捉蟲動態·pidfile丟失問題分析MySql
- 資料庫核心月報-2015/09-MySQL·捉蟲動態·建表過程中crash造成重建表失敗資料庫MySql
- MySQL·捉蟲動態·唯一鍵約束失效MySql
- MySQL·捉蟲動態·DROPDATABASE外來鍵約束的GTIDBUGMySqlDatabaseTiDB
- MySQL啟動失敗MySql
- 爬蟲代理IP自動分配失敗的原因爬蟲
- MySQL Study之–Mysql啟動失敗“mysql.host”薦MySql
- 資料庫核心月報-2015/07-MySQL·社群動態·MySQL記憶體分配支援NUMA資料庫MySql記憶體
- mysql(mariadb)啟動失敗解決方法MySql
- MySQL核心月報2015.02-MySQL·答疑釋惑·InnoDB丟失自增值MySql
- MySQL binlog基於時間點恢復資料失敗是什麼鬼?MySql
- 【MySQL】重放binlog故障一則 ERROR 1050 (42S01) : Table '' already existsMySqlError
- docker啟動失敗Docker
- Win7 Nginx啟動失敗 cmd命令失敗Win7Nginx
- Web伺服器捉蟲速記Web伺服器
- sock鎖檔案導致的MySQL啟動失敗MySql
- Mysql備份失敗案例(一)MySql
- jwc令牌報錯生成失敗
- dota2啟動失敗 初始化vulkan失敗
- Linux靜態Ip配置失敗Linux
- tomcat 啟動失敗Tomcat
- 子執行緒 UI 問題捉蟲執行緒UI
- MySQL建立表失敗的問題MySql
- Windows系統解決PhPStudy MySQL啟動失敗問題WindowsPHPMySql
- CentOS 7下MySQL服務啟動失敗的解決思路CentOSMySql
- sqlplus啟動失敗SQL
- beego自動建表失敗Go
- linux smartd啟動失敗Linux
- 資料安全(反爬蟲)之「防重放」策略爬蟲
- 【Xtrabackup捉蟲】Waiting for master thread to be suspendedAIASTthread
- W32DASM8.93捉蟲記 湖北 wuhuashangASM
- HG_REPMGR啟動失敗排查和狀態檢查步驟
- 高併發mysql update操作必定失敗MySql
- mysql遠端連結失敗筆記MySql筆記
- 遠端主機mysql連線失敗MySql
- Nginx 動態模組 nginx-mod-http-image-filter 載入失敗解決NginxHTTPFilter
- 動態和靜態設定binlog模式及詳解模式
- Oracle RAC啟動失敗(DNS故障)OracleDNS