我有一个基于Spring的JdbcTemplate道下面的代码 -如何在Spring中对两个查询使用相同的连接?
getJdbcTemplate().update("Record Insert Query...");
int recordId = getJdbcTemplate().queryForInt("SELECT last_insert_id()");
的问题是,我有时我的更新和queryForInt查询开始使用连接池中的不同连接执行。
这会导致返回不正确的recordId,因为MySql last_insert_id()应该从发出插入查询的同一个连接调用。
我已经考虑过SingleConnectionDataSource,但不想使用它,因为它降低了应用程序的性能。我只想要这两个查询的单一连接。并非针对所有服务的所有请求。
所以我有两个问题:
- 我可以管理模板类使用的连接?
- JdbcTemplate是否执行自动事务管理?如果我手动将事务应用于我的Dao方法,是否意味着每个查询都会创建两个事务?
希望你们可以对这个话题有所了解。
更新 - 我试过nwinkler的方法,并在事务中包裹了我的服务层。我很惊讶地发现在某个时间之后再次出现同样的问题。挖成春源代码,我发现这一点 -
public <T> T execute(PreparedStatementCreator psc, PreparedStatementCallback<T> action)
throws DataAccessException {
//Lots of code
Connection con = DataSourceUtils.getConnection(getDataSource());
//Lots of code
}
所以相反的是我想,有没有必要每个事务的数据库连接,但对于执行的每个查询的一个连接。 这使我回到我的问题。我想从同一个连接执行两个查询。 :-(
更新 -
<bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource"
destroy-method="close">
<property name="driverClassName" value="${db.driver}" />
<property name="url" value="${db.jdbc.url}" />
<property name="username" value="${db.user}" />
<property name="password" value="${db.password}" />
<property name="maxActive" value="${db.max.active}" />
<property name="initialSize" value="20" />
</bean>
<bean id="jdbcTemplate" class="org.springframework.jdbc.core.JdbcTemplate"
autowire="byName">
<property name="dataSource">
<ref local="dataSource" />
</property>
</bean>
<bean id="transactionManager"
class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
<property name="dataSource" ref="dataSource" />
</bean>
<tx:advice id="transactionAdvice" transaction-manager="transactionManager">
<tx:attributes>
<tx:method name="*" propagation="REQUIRES_NEW" rollback-for="java.lang.Exception" timeout="30" />
</tx:attributes>
</tx:advice>
<aop:config>
<aop:pointcut id="pointcut" expression="execution(* service.*.*(..))" />
<aop:pointcut id="pointcut2" expression="execution(* *.ws.*.*(..))" />
<aop:advisor pointcut-ref="pointcut" advice-ref="transactionAdvice" />
<aop:advisor pointcut-ref="pointcut2" advice-ref="transactionAdvice" />
</aop:config>
嗯,那么我想你还在做错事。你可以发布你的Spring配置,包括数据源和事务管理吗? Spring的片段来自哪个类?你在哪里找到这个? – nwinkler 2012-04-01 09:13:45
该代码来自JdbcTemplate类。每当执行查询时调用它,因此我怀疑。 – 2012-04-02 04:08:28
请看看我更新的答案... – nwinkler 2012-04-02 06:22:56