spring事物深刻了解

1.問題

  一、之前對事物的瞭解只是停留在聲明式事物,配置xml,或使用註解,事物的傳播行爲也只用過REQUIRED和SUPPORTS,能夠說對事物的瞭解很模糊。java

  二、直到在開發中遇到問題。。spring

    問題的描述是:編程

      年末跑定時任務,獲取用戶年末過時積分,併發送積分即將過時的消息提示;緩存

      過時積分作記錄,並與積分作關聯記錄,涉及兩表的操做;springboot

      數據量較多,循環保存,要作到每次循環都會手動提交,而不是作緩存最後提交;併發

      事物的傳播行爲爲默認的REQUIRED,二兩個表操做涉及到了嵌套事物;ide

      So。。。優化

    解決辦法:spa

      1聲明式事物方式.net

       @Transactional(propagation = Propagation.REQUIRES_NEW) 

      2採用了編程式事物

      事物的傳播行爲選擇爲:PROPAGATION_REQUIRES_NEW

public boolean updateExpireCredit(Credit credit) throws Exception {
        // 事務開始-方法級別
        DefaultTransactionDefinition def = new DefaultTransactionDefinition();
        // 傳播行爲: 新建事務,若是當前存在事務,把當前事務掛起
        def.setPropagationBehavior(TransactionDefinition.PROPAGATION_REQUIRES_NEW);
        def.setTimeout(30);
        // 事務狀態
        TransactionStatus status = tm.getTransaction(def);
        boolean falg = false;
        try {
            creditRepository.save(credit);
            tm.commit(status);
            falg = true;
        } catch (Exception e) {
            e.printStackTrace();
            log.error("出現異常,事務回滾:{}", e);
            if (!status.isCompleted()) {
                tm.rollback(status);
            }
            throw e;
        }
        return falg;
    }
View Code

 

2.事物的四個特性(ACID)

  • 原子性(Atomicity):事務是一個原子操做,由一系列動做組成。事務的原子性確保動做要麼所有完成,要麼徹底不起做用。
  • 一致性(Consistency):一旦事務完成(無論成功仍是失敗),系統必須確保它所建模的業務處於一致的狀態,而不會是部分完成部分失敗。在現實中的數據不該該被破壞。
  • 隔離性(Isolation):可能有許多事務會同時處理相同的數據,所以每一個事務都應該與其餘事務隔離開來,防止數據損壞。
  • 持久性(Durability):一旦事務完成,不管發生什麼系統錯誤,它的結果都不該該受到影響,這樣就能從任何系統崩潰中恢復過來。一般狀況下,事務的結果被寫到持久化存儲器中。

3.spring事物管理

  PlatformTransactionManager

    jdbc——org.springframework.jdbc.datasource.DataSourceTransactionManager

    hibernate——HibernateTransactionManager

    jpa——org.springframework.orm.jpa.JpaTransactionManager

    java的jta——org.springframework.transaction.jta.JtaTransactionManager


 


4.事物屬性

  TransactionDefinition接口內容以下:

public interface TransactionDefinition {
    int getPropagationBehavior(); // 返回事務的傳播行爲
    int getIsolationLevel(); // 返回事務的隔離級別,事務管理器根據它來控制另一個事務能夠看到本事務內的哪些數據
    int getTimeout();  // 返回事務必須在多少秒內完成
    boolean isReadOnly(); // 事務是否只讀,事務管理器可以根據這個返回值進行優化,確保事務是隻讀的
}

4.1傳播行爲

  

注:PROPAGATION_REQUIRES_NEW 和 PROPAGATION_NESTED 的最大區別在於, PROPAGATION_REQUIRES_NEW 徹底是一個新的事務, 而 PROPAGATION_NESTED 則是外部事務的子事務, 若是外部事務 commit, 嵌套事務也會被 commit, 這個規則一樣適用於 roll back.

 4.2隔離級別

  併發事務所致使的問題

在同一個應用程序或者不一樣應用程序中的多個事務在同一個數據集上併發執行時,可能會出現許多意外的問題。

併發事務所致使的問題能夠分爲如下三類:

① 髒讀:髒讀發生在一個事務讀取了另外一個事務改寫但尚未提交的數據時。若是改寫在稍後被回滾了,那麼第一個事務獲取的數據就是無效的

② 不可重複讀:不可重複讀發生在一個事務執行相同的查詢兩次或兩次以上,可是每次都獲得不一樣的數據時。這一般是由於另外一個併發事務在兩次查詢期間更新了數據

③ 幻讀:幻讀與不可重複讀相似。它發生在一個事務(T1)讀取了幾行數據,接着另外一個併發事務(T2)插入了一些數據時。在隨後的查詢中,第一個事務(T1)就會發現多了一些本來不存在的記錄

注:

  不可重複讀的重點是修改

  幻讀的重點在於新增或者刪除

 

5.事物狀態

  PlatformTransactionManager接口的getTransaction()的方法獲得的是TransactionStatus接口的一個實現,這個接口的內容以下:

public interface TransactionStatus{
    boolean isNewTransaction(); // 是不是新的事物
    boolean hasSavepoint(); // 是否有恢復點
    void setRollbackOnly();  // 設置爲只回滾
    boolean isRollbackOnly(); // 是否爲只回滾
    boolean isCompleted; // 是否已完成
}

6.編程時事物和聲明式事物

  http://blog.didispace.com/springboottransactional/

  https://blog.csdn.net/trigl/article/details/50968079#t7

相關文章
相關標籤/搜索