ホームページ  >  記事  >  Java  >  SpringBootトランザクション管理例の分析

SpringBootトランザクション管理例の分析

WBOY
WBOY転載
2023-05-13 14:13:20582ブラウズ

1. トランザクションの定義

トランザクションとは、一連の N 段階のデータベース操作から構成される論理的な実行単位であり、この一連の操作はすべて実行されるか、すべて中止されます。

2. トランザクションの特性

トランザクションの特性ACID:

  • 原子性: トランザクションはアプリケーション内で分割できません 最小限の実行body

  • 整合性: トランザクションの実行の結果、データはある整合性状態から別の整合性状態に変更される必要があります

  • 分離永続性: 実行各トランザクションは互いに干渉せず、トランザクションの内部操作は他のトランザクションから分離されます

  • 永続性: トランザクションが送信されると、データへの変更はすべて記録される必要があります。永続ストレージ

3. トランザクションの分離

一般的な同時実行例外

  • 最初のタイプの更新の喪失、2 番目のタイプの更新の喪失更新の喪失

  • #ダーティ リード、非反復読み取り、ファントム リード

#一般的な分離レベル

    #Read Uncommitted: コミットされていないデータの読み取り
  • #Read Committed: 送信されたデータの読み取り
  • #Repeatable Read: 反復可能な読み取り

  • Serializable: Serialization

  • 最初のタイプの更新損失: トランザクションのロールバックにより、別のトランザクションに更新データが失われます。

  • 2 番目のタイプの更新損失: 特定のトランザクションの送信により、別のトランザクションによって更新されたデータが失われます。

ダーティ リード: 特定のトランザクションが別のトランザクションからコミットされていないデータを読み取ります。

反復不可能な読み取り: 特定のトランザクションが前後で同じデータを読み取る結果は一貫性がありません。

ファントム読み取り: 特定のトランザクションで、同じテーブルの前後でクエリされた行数が不一致です。

分離レベル最初のタイプの失われた更新##コミットされていない読み取りはいはいYesYesYesNo##はい繰り返し読み取り##NoNoNoYesRepeatable ReadNoNoNoNoNo共有ロック (S ロック): トランザクション A が特定のデータに共有ロックを追加した後、他のトランザクションはデータに共有ロックを追加することしかできませんが、排他ロックを追加することはできません。
ダーティ リード 2 番目のタイプの失われた更新 繰り返し不可能な読み取り ファントム読み取り
##コミット済みの読み取り No
はい#はい ##No
4. トランザクション管理 実装メカニズム 悲観的ロック (データベース)

排他ロック (X ロック): トランザクション A が特定のデータに排他ロックを追加した後、他のトランザクションはそのデータに共有ロックも排他ロックも追加できません。

オプティミスティック ロック (カスタム)

  • バージョン番号、タイムスタンプなど

  • 更新前データを取得する際は、バージョン番号が変更されているかどうかを確認してください。変更が発生した場合は、この更新をキャンセルします。それ以外の場合は、データを更新します (バージョン番号 1)

#Spring トランザクション管理

宣言トランザクション
  • XML 構成を通じてメソッドのトランザクション特性を宣言します。

  • アノテーションを使用してメソッドのトランザクション特性を宣言します。

プログラムによるトランザクション

    TransactionTemplate を通じてトランザクションを管理し、それを通じてデータベース操作を実行します。
  • 5.例
  • package com.nowcoder.community.service;
    import com.nowcoder.community.dao.AlphaDao;
    import com.nowcoder.community.dao.DiscussPostMapper;
    import com.nowcoder.community.dao.UserMapper;
    import com.nowcoder.community.entity.DiscussPost;
    import com.nowcoder.community.entity.User;
    import com.nowcoder.community.util.CommunityUtil;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.context.annotation.Scope;
    import org.springframework.stereotype.Service;
    import org.springframework.transaction.TransactionDefinition;
    import org.springframework.transaction.TransactionStatus;
    import org.springframework.transaction.annotation.Isolation;
    import org.springframework.transaction.annotation.Propagation;
    import org.springframework.transaction.annotation.Transactional;
    import org.springframework.transaction.support.TransactionCallback;
    import org.springframework.transaction.support.TransactionTemplate;
    import javax.annotation.PostConstruct;
    import javax.annotation.PreDestroy;
    import java.util.Date;
    @Service
    //@Scope("prototype")
    public class AlphaService {
        @Autowired
        private AlphaDao alphaDao;
        @Autowired
        private UserMapper userMapper;
        @Autowired
        private DiscussPostMapper discussPostMapper;
        @Autowired
        private TransactionTemplate transactionTemplate;
        public AlphaService() {
    //        System.out.println("实例化AlphaService");
        }
        @PostConstruct
        public void init() {
    //        System.out.println("初始化AlphaService");
        }
        @PreDestroy
        public void destroy() {
    //        System.out.println("销毁AlphaService");
        }
        public String find() {
            return alphaDao.select();
        }
        // REQUIRED: 支持当前事务(外部事务),如果不存在则创建新事务.
        // REQUIRES_NEW: 创建一个新事务,并且暂停当前事务(外部事务).
        // NESTED: 如果当前存在事务(外部事务),则嵌套在该事务中执行(独立的提交和回滚),否则就会REQUIRED一样.
        @Transactional(isolation = Isolation.READ_COMMITTED, propagation = Propagation.REQUIRED)
        public Object save1() {
            // 新增用户
            User user = new User();
            user.setUsername("alpha");
            user.setSalt(CommunityUtil.generateUUID().substring(0, 5));
            user.setPassword(CommunityUtil.md5("123" + user.getSalt()));
            user.setEmail("alpha@qq.com");
            user.setHeaderUrl("https://cache.yisu.com/upload/information/20220823/112/6198.png");
            user.setCreateTime(new Date());
            userMapper.insertUser(user);
            // 新增帖子
            DiscussPost post = new DiscussPost();
            post.setUserId(user.getId());
            post.setTitle("Hello");
            post.setContent("新人报道!");
            post.setCreateTime(new Date());
            discussPostMapper.insertDiscussPost(post);
            Integer.valueOf("abc");
            return "ok";
        }
        public Object save2() {
            transactionTemplate.setIsolationLevel(TransactionDefinition.ISOLATION_READ_COMMITTED);
            transactionTemplate.setPropagationBehavior(TransactionDefinition.PROPAGATION_REQUIRED);
            return transactionTemplate.execute(new TransactionCallback<Object>() {
                @Override
                public Object doInTransaction(TransactionStatus status) {
                    // 新增用户
                    User user = new User();
                    user.setUsername("beta");
                    user.setSalt(CommunityUtil.generateUUID().substring(0, 5));
                    user.setPassword(CommunityUtil.md5("123" + user.getSalt()));
                    user.setEmail("beta@qq.com");
                    user.setHeaderUrl("https://cache.yisu.com/upload/information/20220823/112/6199.png");
                    user.setCreateTime(new Date());
                    userMapper.insertUser(user);
                    // 新增帖子
                    DiscussPost post = new DiscussPost();
                    post.setUserId(user.getId());
                    post.setTitle("你好");
                    post.setContent("我是新人!");
                    post.setCreateTime(new Date());
                    discussPostMapper.insertDiscussPost(post);
                    Integer.valueOf("abc");
                    return "ok";
                }
            });
        }
    }

以上がSpringBootトランザクション管理例の分析の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

声明:
この記事はyisu.comで複製されています。侵害がある場合は、admin@php.cn までご連絡ください。