最近基于 WebMagic 在做一个爬虫项目。在一个接口中开启爬虫爬一个网站,用的阻塞模式。
之前都没有任何问题,但是最近新的一个网站,因为爬取的时间在 30 分钟左右,等爬完了,做数据持久化操作的时候,就抛出了连接超时被关闭的异常。
希望有遇到过这种情况的大神朋友能给点解决思路。
异常如下: c.z.hikari.pool.ProxyConnection - [153] - DatebookHikariCP - Connection com.mysql.cj.jdbc.ConnectionImpl@215164ec marked as broken because of SQLSTATE(08S01), ErrorCode(0) com.mysql.cj.jdbc.exceptions.CommunicationsException: The last packet successfully received from the server was 1,946,875 milliseconds ago. The last packet sent successfully to the server was 1,946,924 milliseconds ago. is longer than the server configured value of 'wait_timeout'. You should consider either expiring and/or testing connection validity before use in your application, increasing the server configured values for client timeouts, or using the Connector/J connection property 'autoReconnect=true' to avoid this problem.
在数据库 url 中添加‘autoReconnect=true’参数,以及配置 hikari 的心跳检测都依然抛出这个错误。感觉很不合理,因为 mysql 数据库默认的超时时间是 8 小时。
下面是我 hikari 的配置 hikari: auto-commit: true connection-test-query: SELECT 1 connection-timeout: 30000 idle-timeout: 30000 max-lifetime: 1800000 maximum-pool-size: 15 minimum-idle: 5
1
hantsy 2020-07-10 21:05:21 +08:00
The last packet sent successfully to the server was 1,946,924 milliseconds ago. is longer than the server configured value of 'wait_timeout'.You should consider either expiring and/or testing connection validity before use in your application, increasing the server configured values for client timeouts, or using the Connector/J connection property 'autoReconnect=true' to avoid this problem.
这已经好直白了。 程序本身肯定有问题。 |
2
zjp 2020-07-10 22:34:32 +08:00
https://blog.shadowland.cn/java/mysql/2017/09/23/cjcommunicationsexception/
autoReconnect 是不推荐的做法,需要的是 testOnBorrow 或者 testWhileIdle 。 The last packet sent successfully to the server was 1,946,924 milliseconds ago. 说明不是 8 小时自动超时,需要检查下是否是数据库主动释放了连接 |
3
seliote 2020-07-10 22:47:53 +08:00
## Maximum lifetime, if not use begin this it will be release
## this value should lower than `show variables like 'wait_timeout';` database.max-lifetime=60000 |
4
Cinleoi OP @hantsy 我参考了报错提示以及 Stack Overflow 上很多的解决方案,都无作用,现在还没定位的就是连接池把连接断开了还是 mysql 断开的
|
5
Cinleoi OP @zjp testOnBorrow 、testWhileldle hikari 没有对应的属性,链接文章推荐的解决方法是换 Tomcat JDBC 连接池,但是目前项目换连接池不太合适
|
7
hantsy 2020-07-11 10:24:54 +08:00
我相信不是连接池的问题,而是你的程序中有线程问题。
|
8
hantsy 2020-07-11 10:28:15 +08:00
@Cinleoi Tomcat 现在切换到 Dbcp2 ( Apache Commons Pool2 )了吗?
如果切换到 Tomcat 的连接池,我建议用 War 部署,使用 Tomcat 本身去管理 DataSource (应用服务器管理服务器资源效率高得多), 程序中用 JDNI 去连接 DataSource 。 |
9
Cinleoi OP @hantsy 暂时没换,还是用的 Hikari 。程序中执行事务操作的代码是在主线程,但是是要等待阻塞的爬虫线程执行完,我想连接应该就是这里导致了等待空闲时间过长,导致被回收了,但是也没有超过 mysql 的 8 小时,着实想不通了
|
10
Jrue0011 2020-07-11 13:28:12 +08:00
hikaricp 推荐 maxlifetime 比数据库的连接超时设置短个几秒,或者把 maxlifetime 设置成 0(无限)试试?
|
11
Cinleoi OP @Jrue0011 试过了,也是不行的。所以就很离谱,那就说明不是 hikari 回收的连接,mysql 的是 8 小时,也远远没达到回收时间。
|
12
running17 2020-07-11 19:36:12 +08:00
ma 一下,之前也遇到这个问题,没能解决,后面就换了 druid
|
13
6IbA2bj5ip3tK49j 2020-07-12 00:30:44 +08:00
testOnBorrow 应该可以解决这个问题。
也有一个很 tricky 的解决方案:写个定时任务时不时查询一下数据库。 |