原創 記錄一次線上Mysql慢查詢問題排查過程

背景

前段時間收到運維反饋,線上Mysql數據庫凌晨時候出現慢查詢的報警,並把原始sql發了過來:html

--去除了業務含義的sql
update test_user set a=1 where id=1;

表數據量200W左右,不是很大,並且是根據主鍵更新。面試

問題排查

  1. 排查Mysql數據庫

我看到sql後第一反應就是是否是數據庫出問題了,每一個小時都有業務,恰恰白天業務高峯時間段正常,凌晨業務量不多時候出問題,讓運維先檢查了數據庫的狀態,反饋是數據庫正常。sql

  1. 排查業務代碼(第一次)

這塊業務代碼比較複雜,並且是別人寫的,第一次看都沒看完,直接在代碼裏打印了各個模塊執行的時間,而後上線。數據庫

  1. 排查業務代碼(第二次)

次日又出現慢查詢了,我趕忙下載了線上日誌,發現整個方法執行時間很長,而後發現執行時間長的代碼有幾行調用其餘服務的代碼,使用的是HttpClient,猜到了緣由,應該是調用其餘超時致使的。微信

說下系統總體流程,微信(A)回調咱們的收銀臺服務(B),收銀臺更新訂單信息並調用業務服務(C)。cookie

出問題緣由是:session

第一次A調用B,B鎖住記錄行並調用C,這個時候C沒有響應,致使A又發送了第二次請求。運維

第二次A調用B,B更新記錄時候發生死鎖,出現慢查詢。分佈式

解決方案

  1. 收銀臺系統B接收回調的方法添加分佈式鎖,保證同一時刻同一訂單隻能更新一次。ui

  2. 收銀臺調用業務服務使用的是HttpClient4.4,默認超時時間60秒,這麼長時間若是對方沒有響應就完了,改爲了5秒,超時立馬返回,不影響其餘業務。

HttpClient4.4版本設置超時時間代碼以下:

HttpPost httpPost = new HttpPost(url);
 RequestConfig.custom().setSocketTimeout(5000).setConnectTimeout(5000).setConnectionRequestTimeout(5000).build();
 httpPost.setConfig(requestConfig);

上面設置了3個超時時間,含義以下:

setConnectTimeout:設置鏈接超時時間,單位毫秒。

setConnectionRequestTimeout:設置從connect Manager獲取Connection 超時時間,單位毫秒。這個屬性是新加的屬性,由於目前版本是能夠共享鏈接池的。

setSocketTimeout:請求獲取數據的超時時間,單位毫秒。 若是訪問一個接口,多少時間內沒法返回數據,就直接放棄這次調用。

最後,按照這兩個方案改造上線後,系統運行正常,問題解決。

推薦閱讀

1.用戶密碼到底要怎麼加密存儲? 2.完全理解cookie、session、token 3.阿里面試官:分別說說微信和淘寶掃碼登陸背後的實現原理? 4.一分鐘帶你瞭解下MyBatis的動態SQL! 5.原創 | 我是如何解決POI解析Excel出現的OOM問題的?


若是以爲文章不錯,但願能夠隨手轉發或者」在看「哦,很是感謝哈!

關注下方公衆號後回覆「1024」,有驚喜哦!

原文出處:https://www.cnblogs.com/haha12/p/12580673.html

相關文章
相關標籤/搜索