在執(zhí)行一個sql文件時(shí)mysql -h 127.0.0.1 -uroot study -e"source b.sql"
骤肛,報(bào)錯MySQL server has gone away
捂刺。上網(wǎng)查解決辦法俏站,按照網(wǎng)上的解決方法一步步操作,最終找到原因并且解決了,覺得有必要總結(jié)下這個問題發(fā)生的原因及解決辦法,避免后面再繼續(xù)踩坑手负。
情況1. MySQL服務(wù)宕機(jī)
執(zhí)行以下命令,查看mysql的運(yùn)行時(shí)長姑尺。
mysql> show global status like 'uptime';
+---------------+-------+
| Variable_name | Value |
+---------------+-------+
| Uptime | 10170 |
+---------------+-------+
uptime數(shù)值很大竟终,表明mysql服務(wù)運(yùn)行很久,說明最近MySQL服務(wù)器沒有重啟過切蟋。
或者查看MySQL的報(bào)錯日志统捶,看看有沒有重啟的信息。
datou:~$ tail /var/log/mysql/error.log
170914 19:44:37 InnoDB: Completed initialization of buffer pool
170914 19:44:37 InnoDB: highest supported file format is Barracuda.
170914 19:44:37 InnoDB: Waiting for the background threads to start
170914 19:44:38 InnoDB: 5.5.57 started; log sequence number 58681764
170914 19:44:38 [Note] Server hostname (bind-address): '127.0.0.1'; port: 3306
170914 19:44:38 [Note] - '127.0.0.1' resolves to '127.0.0.1';
170914 19:44:38 [Note] Server socket created on IP: '127.0.0.1'.
170914 19:44:38 [Note] Event Scheduler: Loaded 0 events
170914 19:44:38 [Note] /usr/sbin/mysqld: ready for connections.
Version: '5.5.57-0ubuntu0.14.04.1' socket: '/var/run/mysqld/mysqld.sock' port: 3306 (Ubuntu)
如果日志沒有相關(guān)信息柄粹,也表明mysql服務(wù)最近沒有重啟過喘鸟,可以繼續(xù)檢查下面幾項(xiàng)情況。
情況2. 連接超時(shí)
如果程序使用的是長連接驻右,則這種情況的可能性會比較大什黑。
即,某個長連接很久沒有新的請求發(fā)起旺入,達(dá)到了server端的timeout兑凿,被server強(qiáng)行關(guān)閉。
此后再通過這個connection發(fā)起查詢的時(shí)候茵瘾,就會報(bào)錯server has gone away礼华。
mysql> show global variables like '%timeout';
+----------------------------+----------+
| Variable_name | Value |
+----------------------------+----------+
| connect_timeout | 10 |
| delayed_insert_timeout | 300 |
| innodb_lock_wait_timeout | 50 |
| innodb_rollback_on_timeout | OFF |
| interactive_timeout | 28800 |
| lock_wait_timeout | 31536000 |
| net_read_timeout | 30 |
| net_write_timeout | 60 |
| slave_net_timeout | 3600 |
| wait_timeout | 28800 |
+----------------------------+----------+
10 rows in set (0.00 sec)
如下命令設(shè)置連接超時(shí)為5秒。
mysql> SET SESSION wait_timeout=5;
Query OK, 0 rows affected (0.00 sec)
再執(zhí)行SELECT NOW();
拗秘,通過這個connection發(fā)起查詢的時(shí)候圣絮,就會報(bào)錯server has gone away。
mysql> SELECT NOW();
ERROR 2006 (HY000): MySQL server has gone away
No connection. Trying to reconnect...
Connection id: 41
Current database: study
+---------------------+
| NOW() |
+---------------------+
| 2017-09-14 23:12:53 |
+---------------------+
1 row in set (0.01 sec)
實(shí)際上wait_timeout=28800雕旨,不是造成文章開頭的原因扮匠。
情況3. 進(jìn)程在server端被主動kill
這種情況和情況2相似,只是發(fā)起者是DBA或者其他job凡涩。發(fā)現(xiàn)有長時(shí)間的慢查詢執(zhí)行kill xxx導(dǎo)致棒搜。
mysql> show global status like 'com_kill';
+---------------+-------+
| Variable_name | Value |
+---------------+-------+
| Com_kill | 0 |
+---------------+-------+
1 row in set (0.00 sec)
情況4. Your SQL statement was too large.
當(dāng)查詢的結(jié)果集超過 max_allowed_packet 也會出現(xiàn)這樣的報(bào)錯。
查看執(zhí)行SQL執(zhí)行文件大小是否超過 max_allowed_packet 活箕,如果超過則需要調(diào)整參數(shù)力麸,或者優(yōu)化語句。
mysql> show global variables like 'max_allowed_packet';
+--------------------+----------+
| Variable_name | Value |
+--------------------+----------+
| max_allowed_packet | 16777216 |
+--------------------+----------+
1 row in set (0.00 sec)
計(jì)算發(fā)現(xiàn)SQL執(zhí)行文件最大只能是16M,而文章開頭執(zhí)行的a.sql有24M克蚂。
修改參數(shù)闺鲸,max_allowed_packet 調(diào)整為28M。
mysql> set global max_allowed_packet=1024*1024*28;
Query OK, 0 rows affected (0.00 sec)
mysql> show global variables like 'max_allowed_packet';
+--------------------+----------+
| Variable_name | Value |
+--------------------+----------+
| max_allowed_packet | 29360128 |
+--------------------+----------+
1 row in set (0.00 sec)
重新再執(zhí)行`mysql -h 127.0.0.1 -uroot study -e"source b.sql"``成功埃叭,說明原因是情況4造成的摸恍。