Announcement Announcement Module
Collapse
No announcement yet.
Using Declarative Transactions - Not just for db operation Page Title Module
Move Remove Collapse
X
Conversation Detail Module
Collapse
  • Filter
  • Time
  • Show
Clear All
new posts

  • Using Declarative Transactions - Not just for db operation

    Hi,

    Using Spring and Hibernate for the first time. Trying to get to grips with declarative transactions. Would appreciate some help.

    My business method needs to insert an object to the database AND send an email relating to the object. If the email fails to despatch (will throw a RemoteException) I need to rollback the database. (Note this isn't the Spring sendMail support - using existing code for that).

    Code:
    public class ActivationCodeManagerImpl implements ActivationCodeManager
    {
        // .... 
       public void saveAndSend(ActivationCode ac) throws RemoteException
        {
            dao.save(ac);
            sendMail.send(ac); // will throw a RemoteException if it can't despatch ac in an email
        }
    }
    From application context xml file:

    Code:
        <!-- Transaction support -->
        <bean id="transactionManager"
            class="org.springframework.orm.hibernate.HibernateTransactionManager">
            <property name="sessionFactory">
                <ref bean="sessionFactory"/>
            </property>
        </bean>
    
        <bean id="activationCodeManagerTarget" class="uk.ac.lse.spring.lfypublicaccounts.bus.ActivationCodeManagerImpl">
            <property name="activationCodeManagerDao">
                <ref bean="activationCodeManagerDao"/>
            </property>
            <property name="sendMail">
                <ref bean="sendMail"/>
            </property>
        </bean>
    
        <bean id="activationCodeManager" class="org.springframework.transaction.interceptor.TransactionProxyFactoryBean">
            <property name="transactionManager">
                <ref bean="transactionManager"/>
            </property>
            <property name="target">
                <ref bean="activationCodeManagerTarget"/>
            </property>
            <property name="transactionAttributes">
                <props>
                    <prop key="saveAndSend">PROPAGATION_REQUIRED</prop>
                </props>
            </property>
        </bean>
    The xml I've pretty much copy/pasted and adapted from examples. My unit test setup makes sure the email fails to send but the desired rollback doesn't happen. I'm not sure if this is because the failure isn't in a Hibernate operation or because the xml isn't declaring whatever would be necessary to catch a RemoteException and rollback on that.

    Appreciate any help.
    Cheers,
    D.

  • #2
    Hi,

    it doesn't matter what causes the exception (hibernate, mailapi,...). Check your sendMail.send(..) function, if it throws a checked Exception you have to tell spring to rollback the transaction:

    Code:
    <bean id="activationCodeManager" class="org.springframework.transaction.interceptor.TransactionProxyFactoryBean">
            <property name="transactionManager">
                <ref bean="transactionManager"/>
            </property>
            <property name="target">
                <ref bean="activationCodeManagerTarget"/>
            </property>
            <property name="transactionAttributes">
                <props>
                    <prop key="saveAndSend">PROPAGATION_REQUIRED,-RemoteException</prop>
                </props>
            </property>
    
        </bean>
    ... just add '-RemoteException' to your TransactionProxyFactoryBean definition

    regards,
    Mario

    Comment


    • #3
      Thanks Mario, that did the trick.

      Do you know where this stuff is documented? I didn't see anything about adding checked exceptions like that in the 1.1.x reference docs and just checked the TransactionProxyFactoryBean API doc which doesn't seem to mention it either. I'd also like to read more about the exact meaning of the PROPAGATION_* values if you (or anyone else) could recommend anything.

      Thanks again,
      D.

      Comment


      • #4
        Take a look at the spring reference docs 1.2, chapter 7.4. Declarative transaction management.
        I couldn't find the transaction attributes and isolation levels there, but they are documented in the javadoc. (see org.springframework.transaction.TransactionDefinit ion).

        regards,
        Mario

        Comment


        • #5
          Thanks again Mario, has been a great help.

          D.

          Comment

          Working...
          X