Rumah  >  Artikel  >  Java  >  Cara menggunakan MyBatisPlus+SpringBoot untuk melaksanakan fungsi penguncian optimistik

Cara menggunakan MyBatisPlus+SpringBoot untuk melaksanakan fungsi penguncian optimistik

WBOY
WBOYke hadapan
2023-05-11 20:46:11841semak imbas

    1. Senario dengan data pusat membeli-belah tidak konsisten

    Jika ada produk di pusat membeli-belah, harga kos ialah 80 yuan dan harga jualan ialah 100 yuan . Pengurus terlebih dahulu memberitahu Xiao Li bahawa dia harus menaikkan harga barang sebanyak 50 yuan. Xiao Li sedang bermain permainan dan ditangguhkan selama sejam. Tepat sejam kemudian, pengurus merasakan bahawa harga produk telah meningkat kepada 150 yuan, yang terlalu tinggi dan mungkin menjejaskan jualan. Juga maklumkan kepada Xiao Wang bahawa anda akan mengurangkan harga produk sebanyak 30 yuan.

    Pada masa ini, Xiao Li dan Xiao Wang mengendalikan sistem bahagian belakang produk pada masa yang sama. Apabila Xiao Li beroperasi, sistem mula-mula mengeluarkan harga produk sebanyak 100 yuan juga beroperasi, dan harga produk yang dikeluarkan juga ialah 100 yuan. Xiao Li menambah 50 yuan pada harga dan menyimpan 100+50=150 yuan dalam pangkalan data Xiao Wang mengurangkan produk sebanyak 30 yuan dan menyimpan 100-30=70 yuan dalam pangkalan data; Ya, jika tiada kunci, operasi Xiao Li akan dilindungi sepenuhnya oleh Xiao Wang.

    Harga produk semasa ialah 70 yuan, iaitu 10 yuan lebih rendah daripada harga kos. Beberapa minit kemudian, lebih daripada 1,000 item produk ini telah dijual dengan cepat, dan bos kehilangan lebih daripada 10,000 yuan.

    2. Tunjukkan proses ini

    1 Tambah jadual produk pada pangkalan data

    CREATE TABLE product
    (
        id BIGINT(20) NOT NULL AUTO_INCREMENT COMMENT '主键ID',
        name VARCHAR(30) NULL DEFAULT NULL COMMENT '商品名称',
        price INT(11) DEFAULT 0 COMMENT '价格',
        version INT(11) DEFAULT 0 COMMENT '乐观锁版本号',
        PRIMARY KEY (id)
    );
    
    INSERT INTO product (id, NAME, price) VALUES (1, '笔记本', 100);

    2 Buat kelas entiti

    @Data
    public class Product {
        private Long id;
        private String name;
        private Integer price;
        private Integer version;
    }

    3 Mapper

    public interface ProductMapper extends BaseMapper<Product> {
        
    }

    4 Ujian

    @RunWith(SpringRunner.class)
    @SpringBootTest
    public class ProductVersionTest {
    	@Resource
    	private ProductMapper productMapper;
    	
    	@Test
    	public void testProductUpdate() {
    	
    	    //1、小李
    	    Product p1 = productMapper.selectById(1L);
    	
    	    //2、小王
    	    Product p2 = productMapper.selectById(1L);
    	
    	    //3、小李将价格加了50元,存入了数据库
    	    p1.setPrice(p1.getPrice() + 50);
    	    int result1 = productMapper.updateById(p1);
    	    System.out.println("小李修改结果:" + result1);
    	
    	    //4、小王将商品减了30元,存入了数据库
    	    p2.setPrice(p2.getPrice() - 30);
    	    int result2 = productMapper.updateById(p2);
    	    System.out.println("小王修改结果:" + result2);
    	
    	    //最后的结果
    	    Product p3 = productMapper.selectById(1L);
    	    System.out.println("最后的结果:" + p3.getPrice());
    	}
    }

    Keluaran akhir ialah 70 yuan, yang berbeza daripada 120 yuan yang dijangkakan oleh pengurus, mengakibatkan kerugian. Penyelesaiannya ialah menggunakan penguncian optimistik

    3 Skim penguncian optimistik

    Tambah medan versi dalam pangkalan data: apabila mengambil rekod, dapatkan versi semasa

    SELECT id,`name`,price,`version` FROM product WHERE id=1

    Apabila mengemas kini. , versi + 1, jika versi dalam pernyataan where tidak betul, Kemas kini gagal

    UPDATE product SET price=price+50, `version`=`version` + 1 WHERE id=1 AND `version`=1

    4 Proses pelaksanaan kunci yang optimis

    1 Ubah suai kelas entiti

    Tambah @Versi anotasi

    @Version
    private Integer version;

    2. Tambahkan pemalam kunci optimistik

    @Configuration
    //@MapperScan("com.koo.modules.*.dao")
    public class MybatisPlusConfig {
    
        /**
         * 新的分页插件,一缓和二缓遵循mybatis的规则,需要设置 MybatisConfiguration#useDeprecatedExecutor = false 避免缓存出现问题(该属性会在旧插件移除后一同移除)
         */
        @Bean
        public MybatisPlusInterceptor mybatisPlusInterceptor() {
            MybatisPlusInterceptor interceptor = new MybatisPlusInterceptor();
            interceptor.addInnerInterceptor(new PaginationInnerInterceptor(DbType.MYSQL));
            //实现乐观锁,保证数据的准确性
            interceptor.addInnerInterceptor(new OptimisticLockerInnerInterceptor());
            return interceptor;
        }
    
        @Bean
        public ConfigurationCustomizer configurationCustomizer() {
            return configuration -> configuration.setUseDeprecatedExecutor(false);
        }
    
    }

    3 Proses pengoptimuman

    (Hakim sama ada kemas kini data kedua berjaya, jika tidak, semula. ambil data untuk kemas kini)

    @RunWith(SpringRunner.class)
    @SpringBootTest
    public class ProductVersionTest {
    	@Resource
    	private ProductMapper productMapper;
    	
    	@Test
    	public void testProductUpdate() {
    	
    	    //1、小李
    	    Product p1 = productMapper.selectById(1L);
    	
    	    //2、小王
    	    Product p2 = productMapper.selectById(1L);
    	
    	    //3、小李将价格加了50元,存入了数据库
    	    p1.setPrice(p1.getPrice() + 50);
    	    int result1 = productMapper.updateById(p1);
    	    System.out.println("小李修改结果:" + result1);
    	
    	    //4、小王将商品减了30元,存入了数据库
    	    p2.setPrice(p2.getPrice() - 30);
    	    int result2 = productMapper.updateById(p2);
    	    System.out.println("小王修改结果:" + result2);
    	
    		if(result2 == 0){//更新失败,重试
    			    System.out.println("小王重试");
    			    //重新获取数据
    			    p2 = productMapper.selectById(1L);
    			    //更新
    			    p2.setPrice(p2.getPrice() - 30);
    			    productMapper.updateById(p2);
    		}
    	    //最后的结果
    	    Product p3 = productMapper.selectById(1L);
    	    System.out.println("最后的结果:" + p3.getPrice());
    	}
    }

    Hasil output ialah 120, data adalah betul

    Atas ialah kandungan terperinci Cara menggunakan MyBatisPlus+SpringBoot untuk melaksanakan fungsi penguncian optimistik. Untuk maklumat lanjut, sila ikut artikel berkaitan lain di laman web China PHP!

    Kenyataan:
    Artikel ini dikembalikan pada:yisu.com. Jika ada pelanggaran, sila hubungi admin@php.cn Padam