記錄線上一次線程hang住問題

線上發現執行某特定任務在某個特定時間點後再也不work。該任務由線程池中線程執行定時週期性調度,根據日誌查看無任何異常。從代碼研判應該無關定時任務框架,由於對提交的定時任務作了wrap,會將異常都catch住,保證下次仍然可以正常調度。php

經過jstack導出堆棧信息,發現問題線程的堆棧信息以下:html

"OperatorDispatch" #338 prio=5 os_prio=0 tid=0x00007f1140d63000 nid=0x2edc runnable [0x00007f101f8cd000]
   java.lang.Thread.State: RUNNABLE
        at java.net.SocketInputStream.socketRead0(Native Method)
        at java.net.SocketInputStream.socketRead(SocketInputStream.java:116)
        at java.net.SocketInputStream.read(SocketInputStream.java:170)
        at java.net.SocketInputStream.read(SocketInputStream.java:141)
        at com.mysql.jdbc.util.ReadAheadInputStream.fill(ReadAheadInputStream.java:101)
        at com.mysql.jdbc.util.ReadAheadInputStream.readFromUnderlyingStreamIfNecessary(ReadAheadInputStream.java:144)
        at com.mysql.jdbc.util.ReadAheadInputStream.read(ReadAheadInputStream.java:174)
        - locked <0x00000006c4a6d190> (a com.mysql.jdbc.util.ReadAheadInputStream)
        at com.mysql.jdbc.MysqlIO.readFully(MysqlIO.java:3008)
        at com.mysql.jdbc.MysqlIO.reuseAndReadPacket(MysqlIO.java:3469)
        at com.mysql.jdbc.MysqlIO.reuseAndReadPacket(MysqlIO.java:3459)
        at com.mysql.jdbc.MysqlIO.checkErrorPacket(MysqlIO.java:3900)
        at com.mysql.jdbc.MysqlIO.sendCommand(MysqlIO.java:2527)
        at com.mysql.jdbc.MysqlIO.sqlQueryDirect(MysqlIO.java:2680)
        at com.mysql.jdbc.ConnectionImpl.execSQL(ConnectionImpl.java:2490)
        - locked <0x00000006c501d648> (a com.mysql.jdbc.JDBC4Connection)
        at com.mysql.jdbc.PreparedStatement.executeInternal(PreparedStatement.java:1858)
        - locked <0x00000006c501d648> (a com.mysql.jdbc.JDBC4Connection)
        at com.mysql.jdbc.PreparedStatement.execute(PreparedStatement.java:1197)
省略

研判出線程hang在socketRead0方法中,仔細排查後發現socketRead0中的timeout爲0,也即沒有超時設定。java

網上對於此問題有很多說法,有的是說讀取大量數據時會出現,須要設置limit。也有人提交了相關的bug,如74379mysql

我卻是以爲深刻理解JDBC的超時設置這篇文章不錯,也傾向於緣由是網絡抖動,但不管如何應用層的應該對socket鏈接設置超時參數。sql

最終在jdbc鏈接串中加上socketTimeout參數設定超時時間。segmentfault

參考

深刻理解JDBC的超時設置
聊聊jdbc socketTimeout的設置網絡

相關文章
相關標籤/搜索