簡體   English   中英

在上一個事務失敗后,hibernate / spring嘗試插入而不是保存(db中的記錄已存在)

[英]hibernate/spring is trying to insert rather than save (record already exists in db) after the previous transaction failed

我有一個批處理接口類,它創建一個休眠會話,如下所示:

Session session = SessionFactoryUtils.getSession(sessionFactory, true);
TransactionSynchronizationManager.bindResource(sessionFactory, new SessionHolder(session));

然后,它調用服務以從DB中獲取對象列表,並在批處理類中遍歷該列表,並對每個對象進行服務調用以對該對象進行一些處理。

在第二個對象上說,某個地方發生了一些nullpointerexception異常,而我在批處理類中捕獲了該異常。 然后我嘗試通過調用HibernateDaoSupport.getSession(false).save(object)處理第三個對象並在服務中嘗試保存該對象-它實際上試圖插入它(並且我得到一個錯誤,因為已經有一條記錄了存在),而不是對其進行更新。

僅當前一個對象失敗時,才會發生這種情況。 如果發生異常,它會在該Hibernate會話中執行某些操作嗎? 有什么想法嗎?

我的應用程序context.xml中包含以下內容

    <bean id="txManager" class="org.springframework.orm.hibernate3.HibernateTransactionManager">
    <property name="sessionFactory" ref="sessionFactory" />
</bean>

<tx:advice id="txAdvice" transaction-manager="txManager">
    <tx:attributes>
        <tx:method name="*" rollback-for="Throwable"/>
    </tx:attributes>
</tx:advice>
<aop:config>
    <aop:pointcut id="serviceMethods" expression="execution(* com.company.service..*.*(..))" />
    <aop:advisor advice-ref="txAdvice" pointcut-ref="serviceMethods" />
</aop:config>

讓spring創建您的會話並管理您的交易。 TransactionSynchornizationManager是您通常不應該使用的東西。

Session.save應該為瞬態實例分配一個標識符,並通過執行插入操作將其持久化。 我很驚訝它沒有在您的第一個服務電話中這樣做。

而且,由於NPE出現在您的服務調用中,因此該事務將回滾(因為您使用<tx:method name="*" rollback-for="Throwable"/> ),這可以解釋后續調用之間的一些差異和失敗的。 我不知道您的前兩行代碼應該做什么,但是正如Bozho所說,您不應自己將資源綁定到TransactionSynchronizationManager。 這是春天的責任。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM