自拍偷在线精品自拍偷,亚洲欧美中文日韩v在线观看不卡

記一次數(shù)據(jù)庫查詢超時(shí)優(yōu)化問題

存儲(chǔ) 存儲(chǔ)軟件
在 myBatis中,statement timeout 的默認(rèn)值是通過 defaultStatementTimeout 屬性進(jìn)行設(shè)置。同時(shí)還可以在 xml 中 select,insert,update標(biāo)簽設(shè)置timeout屬性,從而對(duì)不同 sql 語句配置超時(shí)時(shí)間。

[[428834]]

本文轉(zhuǎn)載自微信公眾號(hào)「潛行前行」,作者cscw 。轉(zhuǎn)載本文請(qǐng)聯(lián)系潛行前行眾號(hào)。

問題發(fā)現(xiàn)

  • 在七月份時(shí),經(jīng)常發(fā)現(xiàn)有幾個(gè)定時(shí)任務(wù)報(bào)錯(cuò),查看了下異常原因,大概定位是數(shù)據(jù)庫執(zhí)行異常。
  1. ### Error querying database.  Cause: com.mysql.jdbc.exceptions.jdbc4.MySQLNonTransientConnectionException: Unsupported command 
  2. ### The error may exist in class path resource [mapper/XXXXXXXXX-Mapper.xml] 
  3. ### The error may involve defaultParameterMap 
  4. ### The error occurred while setting parameters 
  5. ### SQL: select t3.cino, t2.sn as orderSn,             t2.provider_id as providerId,             t4.logistics_no as logisticsSn,             t2.`name`,       
  6. ### Cause: com.mysql.jdbc.exceptions.jdbc4.MySQLNonTransientConnectionException: Unsupported command 
  7. ; Unsupported command; nested exception is com.mysql.jdbc.exceptions.jdbc4.MySQLNonTransientConnectionException: Unsupported command 
  8. org.springframework.dao.DataAccessResourceFailureException:  
  9. ### Error querying database.  Cause: com.mysql.jdbc.exceptions.jdbc4.MySQLNonTransientConnectionException: Unsupported command 
  10. ### The error may exist in class path resource [mapper/XXXXXXXXXOMapper.xml] 
  11. ### The error may involve defaultParameterMap 
  12. ### The error occurred while setting parameters 
  13. ### SQL: select t3.cino, t2.sn as orderSn,             t2.provider_id as providerId,             t4.logistics_no as logisticsSn,          
  14. ### Cause: com.mysql.jdbc.exceptions.jdbc4.MySQLNonTransientConnectionException: Unsupported command 

排查原因

  • 1 和 DBA 排查 mycat(公司使用 mycat ) 和 mysql 的錯(cuò)誤日志。發(fā)現(xiàn)是應(yīng)用服務(wù)這邊會(huì)給 MyCat 發(fā)送一個(gè) KILL QUERY 命令,而 myCat 不支持該 KILL QUERY 命令。才給應(yīng)用服務(wù)返回了 Unsupported command 異常錯(cuò)誤
  1. 2021-07-02 10:46:33.567  WARN [$_NIOREACTOR-37-RW] (io.mycat.server.ServerQueryHandler.query(ServerQueryHandler.java:96)) - Unsupported command:KILL QUERY 2956587 
  • 2 上網(wǎng)搜索了下 KILL QUERY 發(fā)生的場景,在一篇文章 ?深入分析JDBC超時(shí)機(jī)制 找到問題所在,sql 執(zhí)行超時(shí),jdbc 會(huì)向 mysql 服務(wù)發(fā)送一個(gè)kill 命令,從而讓 mysql 停止 sql 執(zhí)行。不過傳給了 mycat 服務(wù),mycat 沒有處理該命令,而是直接報(bào)錯(cuò)返回
  • 3 查看了下應(yīng)用服務(wù)的配置,在 jdbc:url 統(tǒng)一配置的 mysql socket 執(zhí)行超時(shí)時(shí)間是 15s。而在 mybatis 單獨(dú)的 sql 執(zhí)行語句配置的設(shè)置更長,是 20s(注意這里的配置是 xml 加 注解的方式)
  • 3.1 mybatis xml里的 sql 語句我單獨(dú)在客戶端執(zhí)行,測(cè)試的 sql 執(zhí)行時(shí)間大概在 6,7 秒左右,是不會(huì)超過 15s 這個(gè)限制的,但是從定時(shí)任務(wù)調(diào)度日志看,每次任務(wù)總體上就執(zhí)行了 8 秒左右,說明 mycat 確實(shí)是在15秒內(nèi)收到超時(shí) KILL 命令,從而導(dǎo)致sql 執(zhí)行失敗

  • 4 想著是不是在其他地方配置超時(shí)。細(xì)看了下 mybatis 的配置,還真有一個(gè)統(tǒng)一 sql 超時(shí)配置,default-statement-timeout = 5
  • 從mybatis 源碼文檔上看,單獨(dú)設(shè)置的 mybatis @Options timeout屬性是會(huì)覆蓋掉在 yml 配置的 default-statement-timeout屬性的。難道是 @Options 沒生效 ?

5 因此決定本地調(diào)試一波。發(fā)現(xiàn) @Options 還真的沒生效,jdbc的 queryTimeout 取值的是 mybatis在yml的 全局配置

解決問題

  • 上面提到, sql 的 statment 混合使用了 mybatis 的注解和xml混合使用。猜測(cè)應(yīng)該是 mybatis 的 注解和xml 使用方式是不兼容的。因此試著在 xml 的 statment 修改了 timeout配置。設(shè)置 timeout = 60。發(fā)現(xiàn) 配置生效了,如下圖圖片:

后面也試著將 sql 放置到 mybatis 的 @Select 注解,去掉 xml 的 statement。@Options 的配置也是可以生效的。mybatis 的@Options 和 xml 是無法同時(shí)生效的,可能 mybatis 其他的注解一樣和 xml 配置不能同時(shí)生效,希望讀者以后能避開這個(gè)坑。

Transaction Timeout、Statement Timeout、Socket timeout 的區(qū)別

  • 上面 mybatis 配置的 timeout 其實(shí)就是Statement Timeout。還有就是在jdbc:url 配置的socketTimeout;其實(shí)還有是spring定義的一個(gè)事務(wù)超時(shí):Transaction Timeout。

它們?nèi)叩年P(guān)系是在怎樣的呢

Statement Timeout

  • statement timeout 是用來限制一條語句 statement 的執(zhí)行時(shí)長,可通過調(diào)用JDBC的java.sql.Statement.setQueryTimeout(int timeout) 進(jìn)行設(shè)置,不過一般是通過ORM框架來進(jìn)行設(shè)置
  • 在 myBatis中,statement timeout 的默認(rèn)值是通過 defaultStatementTimeout 屬性進(jìn)行設(shè)置。同時(shí)還可以在 xml 中 select,insert,update標(biāo)簽設(shè)置timeout屬性,從而對(duì)不同 sql 語句配置超時(shí)時(shí)間

Transaction Timeout

  • Spring 提供的 transaction timeout 配置也非常簡單,它會(huì)記錄每個(gè)事務(wù)的開始時(shí)間和消耗時(shí)間,當(dāng)超出timeout值時(shí)將拋出異常。
  • 假設(shè)某個(gè)事務(wù)中包含 3 個(gè)statement,每個(gè)statement的執(zhí)行時(shí)間是 100ms,其他業(yè)務(wù)邏輯的執(zhí)行時(shí)間是 50ms,那么transaction timeout至少應(yīng)該設(shè)置為350ms(100 * 3 + 50)

Socket timeout

  • JDBC的 socket timeout 在數(shù)據(jù)庫被突然停掉或是發(fā)生網(wǎng)絡(luò)錯(cuò)誤時(shí)十分重要。由于TCP/IP的結(jié)構(gòu)原因,socket沒有辦法探測(cè)到網(wǎng)絡(luò)錯(cuò)誤,因此應(yīng)用也無法主動(dòng)發(fā)現(xiàn)數(shù)據(jù)庫連接斷開。如果沒設(shè)置 socket timeout 的話,應(yīng)用在數(shù)據(jù)庫返回結(jié)果前會(huì)無期限地等下去,這種連接被稱為 dead connection

優(yōu)先級(jí)順序

  • Socket timeout 級(jí)別優(yōu)于 Transaction Timeout,而Transaction Timeout 級(jí)別優(yōu)于 Statement Timeout。也就是說如果 Statement Timeout 大于 Transaction Timeout 或者 Socket timeout,則無法生效
  • 不推薦使用socket timeout來限制statement的執(zhí)行時(shí)長,因此socket timeout的值必須要高于statement timeout,否則,socket timeout將會(huì)先生效,這樣statement timeout就變得毫無意義

參考文章

深入分析JDBC超時(shí)機(jī)制 

如何配置MySQL數(shù)據(jù)庫超時(shí)設(shè)置

 

責(zé)任編輯:武曉燕 來源: 潛行前行
相關(guān)推薦

2019-08-19 01:34:38

數(shù)據(jù)庫SQL數(shù)據(jù)庫優(yōu)化

2019-12-02 08:09:57

境數(shù)據(jù)庫連接超時(shí)自動(dòng)回收

2023-11-29 12:12:24

Oceanbase數(shù)據(jù)庫

2019-09-27 17:24:26

數(shù)據(jù)庫優(yōu)化sql

2020-02-10 10:15:31

技術(shù)研發(fā)指標(biāo)

2011-08-08 13:31:44

數(shù)據(jù)分析數(shù)據(jù)倉庫

2018-07-11 10:24:33

數(shù)據(jù)恢復(fù)數(shù)據(jù)刪除

2018-12-06 16:25:39

數(shù)據(jù)庫服務(wù)器線程池

2020-08-24 07:34:39

網(wǎng)絡(luò)超時(shí)請(qǐng)求

2018-02-23 13:41:05

數(shù)據(jù)庫MySQL數(shù)據(jù)恢復(fù)

2011-02-22 09:29:23

jQueryJavaScript

2019-11-22 08:05:01

數(shù)據(jù)庫mysql分區(qū)

2023-04-06 07:53:56

Redis連接問題K8s

2019-11-18 13:42:55

MySQL數(shù)據(jù)庫遷移

2019-09-11 08:22:57

MySQL數(shù)據(jù)庫遠(yuǎn)程登錄

2021-01-08 13:52:15

Consul微服務(wù)服務(wù)注冊(cè)中心

2019-12-16 07:18:42

數(shù)據(jù)庫SQL代碼

2019-12-12 10:38:10

mysql數(shù)據(jù)庫nnodb

2019-11-28 08:31:21

Oracle數(shù)據(jù)庫索引

2019-04-04 15:00:40

SQL索引數(shù)據(jù)庫
點(diǎn)贊
收藏

51CTO技術(shù)棧公眾號(hào)