MYSQL連接一段時間不操作后出現異常的解決方案


  • 最近做的網站使用的是MYSQL數據庫 發現 果超過8小時應用程序不去訪問數據庫,數據庫就斷掉連接 。這時再次訪問就會拋出異常,如下所示:

    com.mysql.jdbc.exceptions.jdbc4.CommunicationsException: Communications link failure
    
    Last packet sent to the server was 0 ms ago.
      at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
      at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:57)
      at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
      at java.lang.reflect.Constructor.newInstance(Constructor.java:525)
      at com.mysql.jdbc.Util.handleNewInstance(Util.java:406)
      at com.mysql.jdbc.SQLError.createCommunicationsException(SQLError.java:1074)
      at com.mysql.jdbc.ConnectionImpl.createNewIO(ConnectionImpl.java:2120)
      at com.mysql.jdbc.ConnectionImpl.<init>(ConnectionImpl.java:723)
      at com.mysql.jdbc.JDBC4Connection.<init>(JDBC4Connection.java:46)
      at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
      at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:57)
      at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
      at java.lang.reflect.Constructor.newInstance(Constructor.java:525)
      at com.mysql.jdbc.Util.handleNewInstance(Util.java:406)
      at com.mysql.jdbc.ConnectionImpl.getInstance(ConnectionImpl.java:302)
      at com.mysql.jdbc.NonRegisteringDriver.connect(NonRegisteringDriver.java:282)
      at java.sql.DriverManager.getConnection(DriverManager.java:579)
      at java.sql.DriverManager.getConnection(DriverManager.java:243)
      at mysql.DBUtil.ConnectAccess(DBUtil.java:29)
      at mysql.DBUtil.getConn(DBUtil.java:15)
      at obj.IndexTurnPic.getAll(IndexTurnPic.java:49)
      at action.GetTurnPic.doAction(GetTurnPic.java:17)
      at maincontrol.MainControlServlet.service(MainControlServlet.java:34)
      at javax.servlet.http.HttpServlet.service(HttpServlet.java:728)
      at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:305)
      at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210)
      at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:222)
      at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:123)
      at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:472)
      at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:171)
      at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:99)
      at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:118)
      at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:408)
      at org.apache.coyote.ajp.AjpProcessor.process(AjpProcessor.java:200)
      at org.apache.coyote.AbstractProtocol$AbstractConnectionHandler.process(AbstractProtocol.java:589)
      at org.apache.tomcat.util.net.JIoEndpoint$SocketProcessor.run(JIoEndpoint.java:310)
      at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1145)
      at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:615)
      at java.lang.Thread.run(Thread.java:722)
    Caused by: com.mysql.jdbc.exceptions.jdbc4.CommunicationsException: Communications link failure

    查了一下發現應用程序和mysql數據庫建立連接,如果超過8小時應用程序不去訪問數據庫,數據庫就斷掉連接 。這時再次訪問就會拋出異常。

    關於mysql自動斷開的問題研究結果如下,在mysql中有相關參數設定,當數據庫連接空閑一定時間后,服務器就會斷開等待超時的連接:

    1、相關參數,紅色部分

    mysql> show variables like '%timeout%';

    +--------------------------+-------+

    | Variable_name            | Value |

    +--------------------------+-------+

    | connect_timeout          | 5     |

    | delayed_insert_timeout   | 300   |

    | innodb_lock_wait_timeout | 50    |

    |  interactive_timeout | 28800 |

    | net_read_timeout         | 30    |

    | net_write_timeout        | 60    |

    | slave_net_timeout        | 3600 |

    |  wait_timeout | 28800 |

    +--------------------------+-------+         

    同一時間,這兩個參數只有一個起作用。到底是哪個參數起作用,和用戶連接時指定的連接參數相關,缺省情況下是使用wait_timeout。我建議是將這兩個參數都修改,以免引起不必要的麻煩。

    2、修改參數

    這兩個參數的默認值是8小時(60*60*8=28800)。我測試過將這兩個參數改為0,結果出人意料,系統自動將這個值設置為1。換句話說,不能將該值設置為永久。

    將這2個參數設置為一年( 31536000 )即可。

    set interactive_timeout= 31536000 ;

    set wait_timeout=

    31536000

    ;

    也可以修改my.cof,修改后重起mysql

    打開/etc/my.cnf,在屬性組mysqld下面添加參數如下:

    [mysqld]

    interactive_timeout= 31536000

    wait_timeout=

    31536000

    如果一段時間內沒有數據庫訪問則mysql自身將切斷連接,之后訪問java訪問連接池時對數據庫的數據通道早就關閉了, 因為dbcp連接池無法時時維護與數據庫的連接關系,mysql5以后即使在dbcp配置中加入autoReconnect=true也沒有效果。


  • 免責聲明!

    本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



     
    粵ICP備18138465號   © 2018-2025 CODEPRJ.COM