2012-07-27 105 views
0

在我的Spring應用程序中,我有服務層方法,標記爲@Transactional(propagation=Propagation.REQUIRED),並使用<tx:annotation-driven />。通常,方法完成時自動提交事務的默認行爲就像魅力一樣。但在特定情況下,我需要在方法結束之前立即提交 - 是的,即使在該點後面出現的部分引發異常。春季交易註釋 - 獲得活躍交易

有沒有辦法在這樣的方法來訪問當前事務?我嘗試這樣做:

TransactionDefinition td = new DefaultTransactionDefinition(TransactionDefinition.PROPAGATION_MANDATORY); // make sure we're talking about the same transaction already provided by the annotation 
TransactionStatus status = transactionManager.getTransaction(td); 

// perform various JDBC operations 

transactionManager.commit(status); 
methodThatNeedsToBeCalledAfterCommit(); 

但通過我的日誌看,我只看到「AbstractPlatformTransactionManager.processCommit(752)|啓動事務提交」發生一次,並從這個似乎是時間戳後methodThatNeedsToBeCalledAfterCommit(),這將是@Transactional方法的正常行爲。

有沒有一種方法可以在這種方法中實際強制進行提交?

回答

1

我不這麼認爲。而且,Spring會在您的方法結束時嘗試重新提交。 所以2提交:不好。

你應該重新考慮你的方法的組織。 也許用2種方法分割現有的一種:一種是@Trnasactional,另一種是剩下的線。

+0

那麼,我不一定會介意最後的承諾。但從設計角度來看,這確實屬於單一方法。 – Dan 2012-07-27 15:30:29

+0

因此,不要使用此方法的註釋並使用手動方式來使用轉換。您將完全控制您的交易。 – 2012-07-27 15:33:39

+0

那麼,我上面的代碼幾乎是在做手動的東西呢?所以我很好。但我希望能夠使用我已經使用的相同事務。特別是,這是因爲此方法也是從具有'@ Rollback'集的JUnit測試中調用的。 – Dan 2012-07-27 15:59:03

0

這可能是因爲默認事務傳播是PROPAGATION_REQUIRED,所以只會在整個事務完成時才提交 - 這是您的外部方法。您可以嘗試PROPAGATION_REQUIRES_NEW:

td.setPropagationBehavior(TransactionDefinition.PROPAGATION_REQUIRED);

另一種方法是使用TransactionTemplate

0

從那裏你想申請交易程序試試這個調用此方法。

 DefaultTransactionDefinition transdefinition = new DefaultTransactionDefinition(); 
     PlatformTransactionManager manager =new PlatformTransactionManager(); 
     TransactionStatus status=null; 




public void beginTransaction() 
    { 

     transdefinition.setPropagationBehavior(0); 


     status = manager.getTransaction(transdefinition); 
    } 

public void commitTransaction() 
    { 
if(status.isCompleted()){ 
manager.commit(status); 
    } 
} 

public void rollbackTransaction() 
    { 
if(!status.isCompleted()){ 
     manager.rollback(status); 
    } 
}