Lokesh
Lokesh

Reputation: 7940

Spring Transaction management

In java Spring, I am facing an issue regarding transaction rollback.

Example:

I have 3 DAOs in my code (A, B, C). All of them extend JDBCTemplate:

@Transaction(propagation=new_required)
public void serviceClassProc() throws Exception {
   A.db1();
   B.db2();
   C.db3();
}   

Now with the above code if I throw an exception in B.db2(), nothing gets rolled back.

Now if I modify B.db2 as following:

@Transaction(propagation=nested,rollbackon=Exception.class)
public void db2() throws Exception{
...
throw new Exception();

}

And then call serviceClassProc(), only the transaction in B.db2, gets rolled back.

I want an implementation where all transactions inside serviceClassProc() get rolled back.

Here are the 2 configurations I am using:

<bean id="bonddao" class="com.marki.bonds.staticdata.dao.MuniStaticDataDaoImpl"> <property name="dataSource" ref="c3p0DataSource" /> </bean> <bean id="dcldao" class="com.bonds.staticdata.dao.DclSettingsDaoImpl"> <constructor-arg ref="c3p0DataSource" /> </bean> <bean id="batchlogdao" class="com.bonds.staticdata.dao.MuniFeedHandlerBatchLogDaoImpl"> <constructor-arg ref="c3p0DataSource" /> </bean>

<bean id="bondsApplication" class="com.markit.bonds.staticdata.service.MuniRefDataSyncApp"> <property name="refdataService" ref="refDataSynchService" /> <property name="mailService" ref="mailSender"></property> <property name="batchLogger" ref="batchlogdao"></property> </bean> <bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager"> <property name="dataSource" ref="c3p0DataSource" /> </bean> <tx:annotation-driven transaction-manager="transactionManager" />

Where I am going wrong? Is it wrong to have 3 DAOs all extending JDBC template? Should all of them share same JDBCTemplate?

Upvotes: 2

Views: 2300

Answers (2)

Tiago Medici
Tiago Medici

Reputation: 2194

you can use also the : **org.springframework.transaction.interceptor.TransactionAspectSupport;**

here is an example that you can handle it:

@Transactional(propagation = Propagation.REQUIRED, isolation = Isolation.READ_COMMITTED, rollbackFor = Exception.class, transactionManager = "transactionManager")
public void messageHandler() {
            try {
                //TODO your own code

            } catch (Exception ex) { 
                TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
            } finally { 

            } 

}

Upvotes: 0

tobiasbayer
tobiasbayer

Reputation: 10379

You should add rollbackon=Exception.class to the annotation of your service method and remove the transaction annotation entirely from the DAO methods. It is a bad idea to have transaction control at DAO level.

Upvotes: 3

Related Questions