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

news/2024/7/3 14:35:18

Transaction Timeout > Statement Timeout > JDBC Driver Socket Timeout

Transaction Timeout指一组SQL操作执行时应在设定的时间内完成(提交或回滚),否则将引发超时。它的值应大于 N(语句数) * Statement Timeout

Statement Timeout指完成单条SQL语句执行的最大允许时间。它的值应小于JDBC Driver Socket Timeout的值,因为后者会被先检查。

最底层的JDBC Driver Socket Timeout指的是通过socket进行连接时的超时或者进行读写操作时的阻塞超时,如果不设置将使用OS层的Socket Timeout值。

超时设置

大部分场景中,应用主要关心Transaction Timeout的设置,除非Transaction中总是只有单条Statement。 超时的具体设置依赖于使用的数据访问框架或者JDBC Driver。如果使用Spring作为基础框架,可以通过为transactionManager的defaultTimeout属性来设置全局的 Transaction Timeout,或者在声明式事务(tx:attributes)的配置中为特定的或所有的方法指定timeout属性的值,还可以在注解式事务@Transactional标记中通过timeout参数来设置。

注意:

1.“ Spring事务超时 = 事务开始时到最后一个Statement创建时时间 + 最后一个Statement的执行时超时时间(即其queryTimeout)。 ” (3)

2. 如果选择JpaTransactionManager作为事务管理器,需要Spring版本在3.0.0之上才能使timeout设置正常工作;

3. 如果选择 DataSourceTransactionManager,事务内所有的sql操作必须通过JdbcTemplate执行才能 使timeout设置正常工作,通过其他orm(如myBatis)执行的sql操作将无法应用超时设置。这种模式下需要按照具体orm框架的要求配置超时(例如myBatis的defaultStatementTimeout 4)

在某些场景中,确实存在混用两种数据访问框架的情况(姑且不讨论这种情况是否合理)。例如在同一事务中混用 JdbcTemplate和MyBatis,在这种场景中,为@Transactional或tx:attributes设置的timeout将不会对非 JdbcTemplate部分的操作生效,因此实际上已无法控制这个事务的超时。此时,有一种“变通”的方式能够使两种数据访问框架能够“共享”超时设 置,那就是设置JDBC Driver Socket阻塞超时。如果使用的是Oracle数据库,并且数据源使用的是DBCP的BasicDataSource,可以在其 connectionProperties属性中设置此值,例如:

<bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource" destroy-method="close">
        <!-- 设置毫秒单位的阻塞超时 -->
        <property name="connectionProperties" value="oracle.net.READ_TIMEOUT=1000"/>  


        <!-- 其他属性设置... -->
</bean>
如果同时有多个属性要设置,在value中通过分号分隔。 其他数据库的设置方式参见资料3。
超时捕获

在Transaction timeout设置生效的情况下,发生超时后,框架将主动回滚当前事务并抛出 UncategorizedSQLException。这是一个RuntimeException的子类,通过其getSql()或getMessage()方法可以得知引发超时的sql语句。

在使用JDBC Driver Socket阻塞超设置时,发生超时后,当前连接将被driver关闭,事务中正在执行的操作,不论是通过JdbcTemplate还是其他ORM框架执 行的,都将引发SQLException(异常信息为:关闭的连接),这个异常将被上层的 TransactionInterceptor捕获并被重新包装成一个 UncategorizedSQLException的实例,随后回滚事务,但由于连接已关闭,因此又会引发回滚异常,所以会看到

“ TransactionInterceptor.completeTransactionAfterThrowing  ( TransactionAspectSu pport.java:414 )

Application exception overridden by rollback exception  ”

最终,会向调用者抛出一个 TransactionSystemException的实例,通过其getApplicationException()方法可以获得被覆盖前的那个 UncategorizedSQLException的实例。

参考资料

1.  Understanding JDBC Internals & Timeout Configuration

2.  Spring transaction timeout doesn't work?

3.  Spring事务超时时间可能存在的错误认识

4.  Using Spring 3 with Mybatis 3 Tutorial – part 1

 

http://www.tuicool.com/articles/y2qIrm


http://www.niftyadmin.cn/n/3297201.html

相关文章

event对象祥解

event代表事件的状态&#xff0c;例如触发event对象的元素、鼠标的位置及状态、按下的键等等。event对象只在事件发生的过程中才有效。event的某些属性只对特定的事件有意义。比如&#xff0c;fromElement 和 toElement 属性只对 onmouseover 和 onmouseout 事件有意义。例子下…

基于HTTP协议的断点续传

> 原理其实断点续传的原理很简单&#xff0c;就是在 Http 的请求上和一般的下载有所不同而已。打个比方&#xff0c;浏览器请求服务器上的一个文时&#xff0c;所发出的请求如下&#xff1a;假设服务器域名为 wwww.sjtu.edu.cn&#xff0c;文件名为 down.zip。GET /down.zip…

oracle java包_java-oracle 调用程序包

Oracle与java.sql.Types的对应Oracle java.sql.Typesblob blobchar charclob clobdate d…

java并发编程--AbstractQueuedSynchronizer加锁和解锁分析(二)

在 java.util.concurrent.locks包中有很多Lock的实现类&#xff0c;常用的有ReentrantLock、 ReadWriteLock&#xff08;实现类ReentrantReadWriteLock&#xff09;&#xff0c;其实现都依赖 java.util.concurrent.AbstractQueuedSynchronizer类&#xff0c;实现思路都大同小异…

Visual Studio 2005 Starter Kits Download

无意中发现几个Visual Studio 2005 Starter Kits下载&#xff0c;包括&#xff1a; Windows Starter Kits: Shareware Starter Kit Web Log Analyzer Starter Kit Card Game Starter Kit Amazon-Enabled Movie Collection Starter Kit Mobile Ink To-Do Starter Kit Vi…

配置SQL Server服务代理来发送存储过程数据 SQL Server Service Broker - z

在SQL Server 2005中&#xff0c;Microsoft引进了一个令人振奋的新特性即服务代理&#xff08;Service Broker&#xff09;&#xff0c;同时这也给许多数据库管理人员带来了一个新的概念。这个概念&#xff0c;进程外消息&#xff0c;是一个开发人员在一些产品中使用多年的应用…

Communications link failure的解决办法

使用Connector/J连接MySQL数据库&#xff0c;程序运行较长时间后就会报以下错误&#xff1a; Communications link failure&#xff0c;The last packet successfully received from the server was *** millisecond ago.The last packet successfully sent to the server was …

用Python Tkinter GUI绘制按钮

1、 import Tkinter GUI绘制类 2、 绘制按钮&#xff0c;设置按钮的属性 3、 向窗口中添加组件&#xff0c;把按钮添加到窗口中 4、 给按钮绑定事件 # !/usr/bin/env python# codingutf-8import Tkinterfrom tkMessageBox import *def save_click(): showinfo(温馨提示,您…