日韩成人免费在线_国产成人一二_精品国产免费人成电影在线观..._日本一区二区三区久久久久久久久不

當前位置:首頁 > 科技  > 軟件

借助Nacos高效配置與實踐Seata事務的TCC模式

來源: 責編: 時間:2024-02-01 12:45:10 289觀看
導讀實現TCC 模式TCC模式與AT模式非常相似,每階段都是獨立事務,不同的是TCC通過人工編碼來實現數據恢復。需要實現三個方法:Try:資源的檢測和預留;Confirm:完成資源操作業務;要求 Try 成功 Confirm 一定要能成功。Cancel:預留資源

實現

TCC 模式

TCC模式與AT模式非常相似,每階段都是獨立事務,不同的是TCC通過人工編碼來實現數據恢復。需要實現三個方法:Tho28資訊網——每日最新資訊28at.com

  • Try:資源的檢測和預留;
  • Confirm:完成資源操作業務;要求 Try 成功 Confirm 一定要能成功。
  • Cancel:預留資源釋放,可以理解為try的反向操作。

流程分析

圖片圖片Tho28資訊網——每日最新資訊28at.com

階段一(Try):檢查余額是否充足,如果充足則凍結金額增加30元,可用余額扣除30Tho28資訊網——每日最新資訊28at.com

圖片圖片Tho28資訊網——每日最新資訊28at.com

圖片圖片Tho28資訊網——每日最新資訊28at.com

此時,總金額 = 凍結金額 + 可用金額,數量依然是100不變,事務直接提交無需等待其它事務。Tho28資訊網——每日最新資訊28at.com

階段二(Confirm) :假如要提交,則凍結金額扣減30Tho28資訊網——每日最新資訊28at.com

圖片圖片Tho28資訊網——每日最新資訊28at.com

確認可以提交,不過之前可用金額已經扣減過了,這里只要清除凍結金額就好了,此時,總金額 = 凍結金額 + 可用金額 = 0 + 70 = 70Tho28資訊網——每日最新資訊28at.com

階段二(Cancel):如果要回滾,則凍結金額扣減30,可用余額增加30Tho28資訊網——每日最新資訊28at.com

圖片圖片Tho28資訊網——每日最新資訊28at.com

需要回滾,那么就要釋放凍結金額,恢復可用金額Tho28資訊網——每日最新資訊28at.com

Seata的TCC模型

圖片圖片Tho28資訊網——每日最新資訊28at.com

代碼樣例

配置和依賴參考之前《利用Nacos實現Seata事務模式(XA與AT)的快速配置與靈活切換》即可Tho28資訊網——每日最新資訊28at.com

bank3:Tho28資訊網——每日最新資訊28at.com

聲明TCC接口@LocalTCCpublic interface AccountInTcc {    @TwoPhaseBusinessAction(name = "prepareDeductMoney", commitMethod = "commitDeductMoney", rollbackMethod = "rollbackDeductMoney")    boolean prepareDeductMoney(BusinessActionContext businessActionContext,                               @BusinessActionContextParameter(paramName = "accountNo")String accountNo,                               @BusinessActionContextParameter(paramName = "amount")Double amount);    /**     * 提交扣款     * 二階段confirm確認方法、可以另命名,但要保證與commitMethod一致     */    boolean commitDeductMoney(BusinessActionContext businessActionContext);    /**     * 回滾扣款     * 二階段回滾方法,要保證與rollbackMethod一致     */    boolean rollbackDeductMoney(BusinessActionContext businessActionContext);}

具體實現:Tho28資訊網——每日最新資訊28at.com

@Componentpublic class AccountInTccImpl implements AccountInTcc {    @Autowired    private AccountInfoMapper accountInfoMapper;    @Transactional    @Override    public boolean prepareDeductMoney(BusinessActionContext businessActionContext, String accountNo, Double amount) {        String xid = businessActionContext.getXid();        // 冪等性判斷        if (TccActionResultWrap.hasPrepareResult(xid)) {            return true;        }        // 避免空懸掛,已經執行過回滾了就不能再預留資源        if (TccActionResultWrap.hasRollbackResult(xid) || TccActionResultWrap.hasCommitResult(xid)) {            return false;        }        // 預留資源        boolean result = accountInfoMapper.prepareDeductMoney(accountNo,amount) > 0;        // 記錄執行結果,以便回滾時判斷是否是空回滾        TccActionResultWrap.prepareSuccess(xid);        System.out.println("============prepare==============");        return result;    }    // 保證提交邏輯的原子性    @Transactional    @Override    public boolean commitDeductMoney(BusinessActionContext businessActionContext) {        String xid = businessActionContext.getXid();        // 冪等性判斷        if (TccActionResultWrap.hasCommitResult(xid)) {            return true;        }        Map<String, Object> actionContext = businessActionContext.getActionContext();        String accountNo = (String) actionContext.get("accountNo");        BigDecimal amount = (BigDecimal) actionContext.get("amount");        // 執行提交操作,扣除預留款        boolean result = accountInfoMapper.commitDeductMoney(accountNo,amount.doubleValue()) > 0;        // 清除預留結果        TccActionResultWrap.removePrepareResult(xid);        // 設置提交結果        TccActionResultWrap.commitSuccess(xid);        System.out.println("============commit==============");        return result;    }    @Transactional    @Override    public boolean rollbackDeductMoney(BusinessActionContext businessActionContext) {        String xid = businessActionContext.getXid();        // 冪等性判斷        if (TccActionResultWrap.hasRollbackResult(xid)) {            return true;        }        // 沒有預留資源結果,回滾不做任何處理;        if (!TccActionResultWrap.hasPrepareResult(xid)) {            // 設置回滾結果,防止空回滾            TccActionResultWrap.rollbackSuccess(xid);            return true;        }        // 執行回滾        Map<String, Object> actionContext = businessActionContext.getActionContext();        String accountNo = (String) actionContext.get("accountNo");        BigDecimal amount = (BigDecimal) actionContext.get("amount");        boolean result = accountInfoMapper.rollbackDeductMoney(accountNo,amount.doubleValue()) > 0;        // 清除預留結果        TccActionResultWrap.removePrepareResult(xid);        // 設置回滾結果        TccActionResultWrap.rollbackSuccess(xid);        System.out.println("============rollback==============");        return result;    }}

業務層:Tho28資訊網——每日最新資訊28at.com

@Autowired  private AccountInTcc accountInTcc;  @Override  public Boolean deductMoney(String accountNo, Double amount) {      return accountInTcc.prepareDeductMoney(null,accountNo,amount);  }

參數中的BusinessActionContext不需要開發人員自己傳遞,直接給null即可,Seata會自動處理。Tho28資訊網——每日最新資訊28at.com

mapper:Tho28資訊網——每日最新資訊28at.com

@Update("update account_info set account_balance = account_balance - #{amount}, frozen_money = frozen_money + #{amount} where account_no = #{accountNo} and account_balance >= #{amount}")    int prepareDeductMoney(@Param("accountNo") String accountNo, @Param("amount") Double amount);    @Update("update account_info set frozen_money = frozen_money - #{amount} where account_no = #{accountNo}")    int commitDeductMoney(@Param("accountNo") String accountNo, @Param("amount") Double amount);    @Update("update account_info set account_balance = account_balance + #{amount}, frozen_money = frozen_money - #{amount} where account_no = #{accountNo}")    int rollbackDeductMoney(@Param("accountNo") String accountNo, @Param("amount") Double amount);

bank4服務調用:Tho28資訊網——每日最新資訊28at.com

@GlobalTransactional    @Override    public Boolean addMoney(String accountNo, Double amount) {        String result = bank3Client.deduct(amount);        if("true".equalsIgnoreCase(result)){            Boolean flag = baseMapper.addMoney(accountNo,amount) > 0;            if(amount != 30 ) throw new RuntimeException("bank4 make exception amount != 30");            return flag;        }        return false;    }

TCC的優點:Tho28資訊網——每日最新資訊28at.com

  • 一階段完成直接提交事務,釋放數據庫資源,性能好
  • 相比AT模型,無需生成快照,無需使用全局鎖,性能最強
  • 不依賴數據庫事務,而是依賴補償操作,可以用于非事務型數據庫

TCC的缺點:Tho28資訊網——每日最新資訊28at.com

  • 有代碼侵入,需要人為編寫try、Confirm和Cancel接口,太麻煩
  • 軟狀態,事務是最終一致
  • 需要考慮Confirm和Cancel的失敗情況,做好冪等處理
  • 空回滾:當某分支事務的try階段阻塞時,可能導致全局事務超時而觸發二階段的cancel操作。在未執行try操作時先執行了cancel操作,這時cancel不能做回滾,就是空回滾
  • 業務懸掛:對于已經空回滾的業務,之前被阻塞的try操作恢復,繼續執行try,就永遠不可能confirm或cancel ,事務一直處于中間狀態,這就是業務懸掛。

圖片圖片Tho28資訊網——每日最新資訊28at.com

執行cancel操作時,應當判斷try是否已經執行,如果尚未執行,則應該空回滾。Tho28資訊網——每日最新資訊28at.com

執行try操作時,應當判斷cancel是否已經執行過了,如果已經執行,應當阻止空回滾后的try操作,避免懸掛。Tho28資訊網——每日最新資訊28at.com

本文鏈接:http://m.www897cc.com/showinfo-26-70394-0.html借助Nacos高效配置與實踐Seata事務的TCC模式

聲明:本網頁內容旨在傳播知識,若有侵權等問題請及時與本網聯系,我們將在第一時間刪除處理。郵件:2376512515@qq.com

上一篇: PHP 高性能的事件循環庫 Revolt

下一篇: Vue3問題:如何實現頁面引導提示?

標簽:
  • 熱門焦點
Top 日韩成人免费在线_国产成人一二_精品国产免费人成电影在线观..._日本一区二区三区久久久久久久久不
国产精品自在欧美一区| 欧美日韩中文字幕日韩欧美| 欧美专区日韩专区| 亚洲激情视频在线播放| 国产精品夜色7777狼人| 欧美精品啪啪| 久久久久欧美精品| 一本久久精品一区二区| 国精品一区二区| 国产伦精品一区二区| 精品成人免费| 好看的日韩av电影| 国内自拍亚洲| 99国产精品| 一本久道久久综合狠狠爱| 亚洲女同精品视频| 一区二区三区精品视频在线观看| 亚洲人成精品久久久久| 激情六月婷婷久久| 一本久道久久久| 久久久久久久久久久一区| 欧美精品日日鲁夜夜添| 国产欧美日韩| 国产日韩欧美三区| 国产视频一区二区在线观看 | 国产一区二区主播在线| 亚洲乱码国产乱码精品精天堂 | 久久欧美中文字幕| 老色鬼精品视频在线观看播放 | 国产精品美女视频网站| 国产精品二区在线| 国产精品久久久久久久久久三级 | 欧美久久一级| 欧美日韩免费一区二区三区视频| 欧美精品在线极品| 国产综合网站| 一区三区视频| 亚洲高清在线视频| 亚洲黑丝在线| 欧美一区成人| 久久精品视频在线看| 久久婷婷综合激情| 免播放器亚洲一区| 欧美激情欧美狂野欧美精品| 欧美另类人妖| 欧美日韩精品是欧美日韩精品| 91久久久精品| 欧美片第1页综合| 日韩午夜免费视频| 欧美一区二区日韩| 欧美资源在线观看| 久久久久99| 毛片一区二区| 欧美精品一区在线观看| 国产一区二区三区四区hd| 亚洲国产高潮在线观看| 欧美有码在线观看视频| 免费的成人av| 国产亚洲在线| 在线成人激情视频| 亚洲精品日韩一| 国产精品99久久久久久宅男| 午夜精品久久久久久99热软件| 久久国产精品久久久久久电车| 久久久久九九九九| 欧美xxx成人| 欧美日韩在线免费视频| 国产欧美精品日韩区二区麻豆天美| 狠狠88综合久久久久综合网| 午夜精品久久久久久久| 欧美成人午夜激情视频| 国产精品激情av在线播放| 国产精品久久久999| 亚洲免费电影在线观看| 久久精品视频99| 亚洲一区999| 欧美一区二区在线视频| 亚洲欧美日韩中文在线制服| 久久国产精品久久久久久电车| 欧美色欧美亚洲高清在线视频| 亚洲日本成人在线观看| 午夜精品福利电影| 国产精品久久精品日日| 海角社区69精品视频| 欧美一区二区视频观看视频| 国产精品私人影院| 午夜精品美女自拍福到在线 | 日韩视频欧美视频| 亚洲尤物视频在线| 免费成人av| 亚洲国产国产亚洲一二三| 亚洲一区精品在线| 免费黄网站欧美| 国产精品一区二区在线观看| 亚洲欧美日韩精品久久亚洲区| 国产精品视频免费| 久久成人免费日本黄色| 在线成人欧美| 欧美韩国在线| 国内精品视频666| 美女视频黄免费的久久| 最新日韩在线| 欧美日韩亚洲一区二区三区在线观看| 正在播放欧美视频| 国产精品乱码| 日韩一级免费观看| 欧美视频一区二区三区| 91久久在线视频| 欧美日韩福利| 亚洲综合日韩中文字幕v在线| 欧美日韩成人综合| 在线观看国产精品网站| 亚洲欧美日韩国产中文在线| 国产欧美日韩高清| 久久在线免费视频| 日韩视频亚洲视频| 国产精品视频在线观看| 亚洲无毛电影| 国产一区清纯| 欧美精品麻豆| 亚洲午夜久久久久久久久电影网| 欧美激情一区二区三区全黄| 亚洲高清激情| 免费一级欧美在线大片| 在线观看成人av电影| 久久久久久综合网天天| 欧美日韩国内| 99re6这里只有精品| 欧美高清在线一区| 亚洲一区二区三区色| 国产精品久久久久婷婷| 久久精品日韩一区二区三区| 91久久午夜| 欧美激情在线| 亚洲欧美一区二区视频| 亚洲电影免费观看高清完整版在线观看 | 亚洲日本在线视频观看| 国产精品久久午夜夜伦鲁鲁| 久久一二三四| 亚洲一区二区不卡免费| 欧美性猛交视频| 亚洲婷婷综合久久一本伊一区| 国产一区亚洲| 欧美午夜剧场| 亚洲综合视频1区| 亚洲高清在线观看| 久久久美女艺术照精彩视频福利播放 | 一区二区三区黄色| 欧美国产日韩视频| 国产日韩欧美不卡| 亚洲美女视频| 国产欧美一区视频| 欧美久久婷婷综合色| 亚洲欧美资源在线| 久久久久久久久一区二区| 亚洲美女黄网| 国产精品国产福利国产秒拍| 欧美影院视频| 久久久久久久999| 日韩午夜中文字幕| 亚洲高清视频在线| 国产亚洲日本欧美韩国| 尤物99国产成人精品视频| 亚洲精品久久久蜜桃 | 狠狠狠色丁香婷婷综合久久五月| 国产综合色产在线精品| 欧美在线视屏| 亚洲日本va午夜在线电影| 国产精品hd| 亚洲欧美另类国产| 伊人春色精品| 国产女人水真多18毛片18精品视频| 亚洲人午夜精品| 国色天香一区二区| 国产精品乱码| 欧美日韩一区二区在线| 欧美大片免费观看| 免费永久网站黄欧美| 夜夜狂射影院欧美极品| 欧美激情视频在线播放 | 欧美激情黄色片| 亚洲精品日产精品乱码不卡| 欧美日韩精品免费观看视频| 亚洲天堂成人在线视频| 亚洲午夜精品久久| 亚洲激情在线观看视频免费| 亚洲中无吗在线| 一区二区激情| 日韩亚洲欧美中文三级| 亚洲一区日韩| 女女同性精品视频| 久久电影一区| 悠悠资源网亚洲青| 亚洲午夜久久久久久尤物| 亚洲人成在线播放| 亚洲国产婷婷| 亚洲国产精品国自产拍av秋霞| 狠狠色香婷婷久久亚洲精品| 国产日产精品一区二区三区四区的观看方式| 欧美天天综合网| 欧美视频一区二| 国产精品久久精品日日| 国产精品视频网站| 久热爱精品视频线路一|