日本综合一区二区|亚洲中文天堂综合|日韩欧美自拍一区|男女精品天堂一区|欧美自拍第6页亚洲成人精品一区|亚洲黄色天堂一区二区成人|超碰91偷拍第一页|日韩av夜夜嗨中文字幕|久久蜜综合视频官网|精美人妻一区二区三区

RELATEED CONSULTING
相關(guān)咨詢
選擇下列產(chǎn)品馬上在線溝通
服務(wù)時間:8:30-17:00
你可能遇到了下面的問題
關(guān)閉右側(cè)工具欄

新聞中心

這里有您想知道的互聯(lián)網(wǎng)營銷解決方案
MySQL 存儲過程中的只讀語句超時怎么辦?

?MySQL 有一個參數(shù)叫 max_execution_time ,用來設(shè)置只讀語句執(zhí)行的超時時間,但是僅對單獨(dú)執(zhí)行的 select 語句有效;對于非單獨(dú)執(zhí)行的 select 語句,比如包含在存儲過程、觸發(fā)器等內(nèi)置事務(wù)塊里則不生效。官方手冊上對這個參數(shù)解釋如下:

成都創(chuàng)新互聯(lián)公司始終致力于在企業(yè)網(wǎng)站建設(shè)領(lǐng)域發(fā)展。秉承“創(chuàng)新、求實(shí)、誠信、拼搏”的企業(yè)精神,致力為企業(yè)提供全面的網(wǎng)絡(luò)宣傳與技術(shù)應(yīng)用整體策劃方案,為企業(yè)提供包括“網(wǎng)站建設(shè)、響應(yīng)式網(wǎng)站、手機(jī)網(wǎng)站建設(shè)、微信網(wǎng)站建設(shè)、重慶小程序開發(fā)、商城網(wǎng)站建設(shè)、平臺網(wǎng)站建設(shè)秉承"和諧、參與、激情"的文化,與客戶和合作伙伴齊心協(xié)力一起成長,共同發(fā)展。

max_execution_time applies as follows:

The global max_execution_time value provides the default for the session value for new connections. The session value applies to SELECT executions executed within the session that include no MAX_EXECUTION_TIME(*N*) optimizer hint or for which N is 0.

max_execution_time applies to read-only SELECT statements. Statements that are not read only are those that invoke a stored function that modifies data as a side effect.

max_execution_time is ignored for SELECT statements in stored programs.

那對這種非單獨(dú)出現(xiàn)的 select 語句,該如何控制超時時間呢?

先來看下參數(shù) max_execution_time 設(shè)置后的效果。此參數(shù)設(shè)置后,select 語句如果執(zhí)行時間過長,會直接被 cancel 掉,并且報(bào)錯,如下所示:

mysql> set @@max_execution_time=1000;
Query OK, 0 rows affected (0.00 sec)

mysql> select sleep(2) from t1 limit 1;
ERROR 3024 (HY000): Query execution was interrupted, maximum statement execution time exceeded

或者是采用直接加 Hint 的方式,也能限制 select 語句的執(zhí)行時間: 下面兩種方式都能起到限制 select 語句執(zhí)行時間的作用。

mysql> select /*+ max_execution_time(1000) */ sleep(2) from t1 limit 2;
ERROR 3024 (HY000): Query execution was interrupted, maximum statement execution time exceeded

mysql> select /*+ set_var(max_execution_time=1000) */ sleep(2) from t1 limit 2;
ERROR 3024 (HY000): Query execution was interrupted, maximum statement execution time exceeded

那如果把這條 select 語句封裝在存儲過程內(nèi)部,按照手冊上對參數(shù) max_execution_time 的解釋,則不生效。比如新建一個存儲過程 sp_test :

DELIMITER $$

USE `ytt`$$

DROP PROCEDURE IF EXISTS `sp_test`$$

CREATE DEFINER=`admin`@`%` PROCEDURE `sp_test`()
BEGIN
select sleep(2) from t1 limit 1;
END$$

DELIMITER ;

重新設(shè)置 max_execution_time 值為1秒:調(diào)用存儲過程 sp_test , 可以正常執(zhí)行,select 語句并沒有被 cancel 掉!

mysql> call sp_test;
+----------+
| sleep(2) |
+----------+
| 0 |
+----------+
1 rows in set (2.01 sec)

Query OK, 0 rows affected (2.01 sec)

那如何解決這個問題呢?

為了更方便大家測試,把語句 select sleep(2) from t1 limit 1 改為 select sleep(2000) from t1 limit 1 。既然 MySQL 層面有這樣的限制,那只能從非 MySQL 層面來想辦法。最直接有效的就是寫個腳本來主動 cancel 掉 select 語句。腳本如下:

root@ytt-normal:/home/ytt/script# cat kill_query 
#!/bin/sh
QUERY_ID=`mysql -ss -e "select id from information_schema.processlist where user='admin' and db='ytt' and time>10 and regexp_like(info,'^select','i')"`
if [ $QUERY_ID ];then
echo "kill query $QUERY_ID"
mysql -e "kill query $QUERY_ID"
fi

完后把腳本放到 crontab 或者 MySQL 自己的 event 里來定時執(zhí)行即可。單獨(dú)執(zhí)行腳本效果如下:

root@ytt-normal:/home/ytt/script# ./kill_query 
kill query 50

除了自己編寫腳本,還有一個工具可以實(shí)現(xiàn)類似的效果,它包含在我們熟知的 Percona-toolkit 工具箱里,叫 pt-kill 。

pt-kill 工具可以根據(jù)各種觸發(fā)條件來執(zhí)行指定動作:比如 cancel 掉指定 SQL 語句、kill 掉指定 session 等。所以完全可以使用 pt-kill 工具來實(shí)現(xiàn) select 語句超時被自動 cancel 掉。如下所示:pt-kill 工具會在后臺一直運(yùn)行,監(jiān)聽 MySQL 進(jìn)程,一旦觸發(fā)條件被激活,即可執(zhí)行相應(yīng)動作。

root@ytt-normal:/home/ytt/script# pt-kill --match-db=ytt --match-user=admin --match-host=%  \--match-info='^select' --victims=all --busy-time='10s' --print --kill-query

# 2022-08-15T17:29:03 KILL QUERY 50 (Query 11 sec) select sleep(2000) from t1 limit 1

有一點(diǎn)需要注意:select 語句超時自動 cancel 掉這樣的功能不適宜用在生產(chǎn)環(huán)境!因?yàn)槟銦o法預(yù)知其執(zhí)行結(jié)果的時效性、上下文是否相關(guān)等特點(diǎn)。?


當(dāng)前名稱:MySQL 存儲過程中的只讀語句超時怎么辦?
分享路徑:http://www.dlmjj.cn/article/djeoiph.html