Announcement Announcement Module
Collapse
No announcement yet.
Transaction propagation question Page Title Module
Move Remove Collapse
X
Conversation Detail Module
Collapse
  • Filter
  • Time
  • Show
Clear All
new posts

  • Transaction propagation question

    Hi guys. Not sure if it's right place for question, but anyway.
    I can't understand how is the propagation mechanism works.
    So, I have an interface
    Code:
    package com.spring.da.tx;
    
    public interface FooService {
    	
    	Foo getFoo(String fooName);
    	
    	Foo getFoo(String fooName, String barName);
    	
    	void noPropagation();
    
    }
    and it's default implementation class:
    Code:
    package com.spring.da.tx;
    
    import org.springframework.transaction.interceptor.TransactionAspectSupport;
    
    public class DefaultFooService implements FooService {
    
    	public Foo getFoo(String fooName) {
    		return new Foo();
    	}
    
    	public Foo getFoo(String fooName, String barName) {
    		throw new UnsupportedOperationException();
    	}
    	
    	public void noPropagation() {
                getFoo("");
    	}
    
    }
    Then here is my context config:
    Code:
    <bean id="fooService" class="com.spring.da.tx.DefaultFooService"/>
        
        <tx:advice id="txAdvice" transaction-manager="txManager">
        	<tx:attributes>
        		<tx:method name="get*" read-only="true" rollback-for="UnsupportedOperationException" propagation="MANDATORY"/>
        	</tx:attributes>
        </tx:advice>
        
        <aop:config>
         	<aop:pointcut id="fooServiceOperation" expression="execution(* com.spring.da.tx.FooService.get*(..))"/>
        	<aop:advisor advice-ref="txAdvice" pointcut-ref="fooServiceOperation"/>
        </aop:config>
        
        <bean id="txManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
    		<property name="dataSource" ref="dataSource"/>
        </bean>
        
        <bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource">
        	<property name="driverClassName" value="com.mysql.jdbc.Driver"/>
        	<property name="url" value="jdbc:mysql://localhost:3306/"/>
        	<property name="username" value="root"/>
        	<property name="password" value="root"/>
        </bean>
    As you can see, only methods which is started with get should be in transaction. Even more, the propagation rule is MANDATORY, that means if no existing transaction is in progress, an exception will be thrown. In the DefaultFooService implementation class I have a non transactional method noPropagation() which calls the transactional (MANDATORY) method getFoo(String).

    When I run this test:
    Code:
    FooService fooService =  (FooService)ctx.getBean("fooService");
    		fooService.noPropagation();
    no exception is thrown. But getFoo is marked as MANDATORY and is called from non transactional method. So why the exception is not thrown?

  • #2
    Have you had a read of this, basically internal method calls and AOP proxies.
    http://www.springframework.org/docs/...ng-aop-proxies

    Comment


    • #3
      Originally posted by karldmoore View Post
      Have you had a read of this, basically internal method calls and AOP proxies.
      http://www.springframework.org/docs/...ng-aop-proxies
      Got you. Thanks. I'll try to change my code slightly, and post the result.

      Comment


      • #4
        Excellent. It works:

        Code:
        Exception in thread "main" org.springframework.transaction.IllegalTransactionStateException: No existing transaction found for transaction marked with propagation 'mandatory'
        ...

        Comment


        • #5
          Fantastic, glad it's working. If you really want internal method calls to be proxied you'd have to look at AspectJ.

          Comment


          • #6
            Originally posted by karldmoore View Post
            Fantastic, glad it's working. If you really want internal method calls to be proxied you'd have to look at AspectJ.
            Unfortunately I can't. Our application still uses JDK 1.4

            Comment

            Working...
            X