聊聊jdbc socketTimeout的设置

本文主要介绍下jdbc的socket timeout的设置

jdbc timeout类别

主要有如下几个类别

transaction timeout

设置的是一个事务的执行时间,里头可能包含多个statement

statement timeout()

设置的是一个statement的执行超时时间,即driver等待statement执行完成,接收到数据的超时时间()

jdbc socket timeout

设置的是jdbc I/O socket read and write operations的超时时间,防止因网络问题或数据库问题,导致driver一直阻塞等待。()

os socket timeout

这个是操作系统级别的socket设置()。

上面的不同级别的timeout越往下优先级越高,也就是说如果下面的配置比上面的配置值小的话,则会优先触发timeout,那么相当于上面的配置值就”失效”了。

jdbc socket timeout

这个不同数据的jdbc driver实现不一样

mysql

通过url参数传递即可

pg

pg也是通过url传递,不过它的单位与mysql不同,mysql是毫秒,而pg是秒

oracle

oracle需要通过oracle.jdbc.ReadTimeout参数来设置,连接超时参数是oracle.net.CONNECT_TIMEOUT

oracle.jdbc.ReadTimeout

driver内部将该值设置到oracle.net.READ_TIMEOUT变量上

可用看到最后设置的是socket的soTimeout

实例

超时错误输出

刚开始会有数据输出,但是到了某个resultSet的next的时候,报了超时(),这个超时指定的是当result.next方法触发新的一批数据的拉取()之后在timeout时间返回内没有收到数据库返回的数据。

oracle的jdbc默认的fetchSize为10,也就是每个fetch,如果超过指定时间没接收到数据,则抛出timeout异常。

小结

jdbc的socketTimeout值的设置要非常小心,不同数据库的jdbc driver设置不一样,特别是使用不同连接池的话,设置也可能不尽相同。对于严重依赖数据库操作的服务来说,非常有必要设置这个值,否则万一网络或数据库异常,会导致服务线程一直阻塞在java.net.SocketInputStream.socketRead0。

如果查询数据多,则会导致该线程持有的data list不能释放,相当于内存泄露,最后导致OOM

如果请求数据库操作很多且阻塞住了,会导致服务器可用的woker线程变少,严重则会导致服务不可用,nginx报504 Gateway Timeout

doc

oracle.jdbc.ReadTimeout

深入理解JDBC的超时设置

在Spring中基于JDBC进行数据访问时如何控制超时

BugFix-HttpURLConnection

  • 发表于:
  • 原文链接:http://kuaibao.qq.com/s/20180122G109NQ00?refer=cp_1026

相关快讯

扫码关注云+社区