Mysql连接超时的问题与解决方法

问题

    com.mysql.jdbc.exceptions.jdbc4.CommunicationsException: Communications link failure
    The last packet successfully received from the server was 4,514,485 milliseconds ago.  The last packet sent successfully to the server was 3 milliseconds ago.

现象说明

按字面意思:Mysql的连接异常,最近一次从mysql获取到数据包是在4,514,485毫秒之前,而最近一次给mysql发送数据包是在 3 毫秒前。

根因分析

这个与mysql的连接被持有了4,514,485毫秒,这段持有时间内没有任何任何的交互,mysql连接一直处于等待状态,mysql有个等待超时的设置,查下:

        show variables like 'wait_timeout'; 

发现wait_timeout这个等待超时时间小于这个mysql连接的持有时间。mysql连接因等待超时,mysql服务器会主动关闭该连接。而客户端并不知晓,认为连接依然有效,并试图发送请求,这时就会抛出这个连接异常信息。

解决方法

方法1

修改mysql服务器配置 wait_timeout,使其足够大

方法2

修改mysql客户端连接的参数配置。客户端连接的url参数建议加上:autoReconnect=true&failOverReadOnly=false

高可用的mysql url参数配置如下表所示:

参数名参数说明缺省值最低版本要求
autoReconnect当数据库连接异常中断时,驱动是否自动重新连接?如果启用,那驱动在抛出连接异常后,在下一个query前会重建好连接,但副作用就是可能会破坏会话状态和数据一致性,除非程序设计时对这种异常有合适的处理。Mysql官方建议直接修改服务器的wait_timeout配置。false1.1
autoReconnectForPools是否使用针对数据库连接池的重连策略false3.1.3
failOverReadOnly自动重连后连接是否设置为‘只读’模式true3.0.12
maxReconnectsautoReconnect为true时,尝试重试连接的最大次数31.1
reconnectAtTxEndautoReconnect为true时,驱动是否每次事务后尝试重连false3.0.10
initialTimeoutautoReconnect为true时,两次尝试重连的时间间隔21.1

failOverReadOnly=false是为了避免在重连后,有数据更新或插入操作在‘read-only’连接中无法执行而抛出新的异常

方法3

在理解方法2的基础上,如果应用了hibernate,则需要配置如下:

<property name="connection.autoReconnect">true</property> 
<property name="connection.autoReconnectForPools">true</property> 
<property name="connection.is-connection-validation-required">true</property>

如果还是用C3P0连接池框架的话,配置如下

<property name="hibernate.c3p0.acquire_increment">1</property> 
<property name="hibernate.c3p0.idle_test_period">0</property> 
<property name="hibernate.c3p0.timeout">0</property> 
<property name="hibernate.c3p0.validate">true</property>

另外,客户端连接中也有一个的超时时间,这个超时时间的配置一定要小于服务端的超时时间配置。

###方法4
优化程序代码,捕获超时异常,进行异常处理。如果方法2和方法3不起作用,那最好的方式就是优化代码,避免在一个连接中执行耗时的操作。

  • 5
    点赞
  • 20
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值