Mybatis-Plus中的乐观锁与悲观锁

乐观锁

乐观锁(Optimistic Lock): 乐观锁是一种通过版本号(Version)或时间戳(Timestamp)来实现的并发控制机制。在更新数据时,会先检查数据版本号或时间戳是否匹配,如果匹配则更新数据并将版本号加一(或更新时间戳),否则认为是数据已经被其他事务修改过,不进行更新操作

乐观锁在Springboot中的实现

1.在数据库表中添加字段version

2.添加乐观锁配置

java 复制代码
        // 配置乐观锁
        interceptor.addInnerInterceptor((new OptimisticLockerInnerInterceptor()));
        return  interceptor;

3.使用注解

java 复制代码
public class Product {

    private Long id;
    private String name;
    private Integer price;
    @Version
    private Integer version;

}

完整代码:

java 复制代码
//实体
package com.qing.mybatislearning.pojo;

import com.baomidou.mybatisplus.annotation.TableName;
import com.baomidou.mybatisplus.annotation.Version;
import lombok.Data;
import org.springframework.stereotype.Repository;

@Data
@TableName("t_product")
public class Product {

    private Long id;
    private String name;
    private Integer price;
    @Version
    private Integer version;

}

//配置类
package com.qing.mybatislearning.config;


import com.baomidou.mybatisplus.annotation.DbType;
import com.baomidou.mybatisplus.extension.plugins.MybatisPlusInterceptor;
import com.baomidou.mybatisplus.extension.plugins.inner.OptimisticLockerInnerInterceptor;
import com.baomidou.mybatisplus.extension.plugins.inner.PaginationInnerInterceptor;
import org.mybatis.spring.annotation.MapperScan;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration
//扫描Mapper接口所在的包
@MapperScan("com.qing.mybatislearning.mapper")
public class MyBatisPlusConfig {
    //  Ctrl + p:查看方法的参数
    @Bean
    public MybatisPlusInterceptor mybatisPlusInterceptor(){
        MybatisPlusInterceptor interceptor = new MybatisPlusInterceptor();
        //分页配置
        // 设置数据库类型为MYSQL,原因是不同数据库的分页方法不同
        interceptor.addInnerInterceptor(new PaginationInnerInterceptor(DbType.MYSQL));
        // 配置乐观锁
        interceptor.addInnerInterceptor((new OptimisticLockerInnerInterceptor()));
        return  interceptor;
    }


}



// 接口
package com.qing.mybatislearning.mapper;

import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.qing.mybatislearning.pojo.Product;
import org.springframework.stereotype.Repository;

@Repository
public interface ProductMapper extends BaseMapper<Product> {

}


//测试类
package com.qing.mybatislearning;

import com.qing.mybatislearning.mapper.ProductMapper;
import com.qing.mybatislearning.pojo.Product;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;

@SpringBootTest
public class MybatisPlusLeGuanSuoTest {

    @Autowired
    private ProductMapper productMapper;

    @Test
    public void Test1(){
        //小李查询商品价格
        Product productLi = productMapper.selectById(1);
        System.out.println("小李获取的产品信息是: " + productLi.getPrice());

        //小王查询商品价格
        Product productWang = productMapper.selectById(1);
        System.out.println("小王获取的产品信息是: " + productWang.getPrice());
        //小李将价格+50
        productLi.setPrice(productLi.getPrice() + 50);
        productMapper.updateById(productLi);
        //小王将价格-30
        productWang.setPrice(productWang.getPrice() - 30);
        int result = productMapper.updateById(productWang);
        if(result == 0){
            Product productWangNew = productMapper.selectById(1);
            productWangNew.setPrice(productWangNew.getPrice() - 30);
            productMapper.updateById(productWangNew);
        }

        //老板查询商品价格
        Product productBoss = productMapper.selectById(1);
        System.out.println("老板获取的产品信息是: " + productBoss.getPrice());
    }
}

悲观锁

悲观锁(Pessimistic Lock): 悲观锁是一种在操作数据之前先加锁的机制,以避免数据被其他事务修改。在 MyBatis-Plus 中,可以通过 selectForUpdate 方法来实现悲观锁的功能,例如:

java 复制代码
User user = userMapper.selectById(userId, new QueryWrapper<User>().forUpdate());

上面的代码会在查询用户数据时加上 for update,使得查询结果被加上排它锁。

总的来说,乐观锁适合并发量不高的场景,通过版本号或时间戳来控制数据的更新;而悲观锁适合并发量高、需要确保数据一致性的场景,通过数据库锁来保证数据的完整性。在实际应用中,可以根据业务需求和系统的并发情况选择合适的锁机制。

相关推荐
独自破碎E15 小时前
Spring Boot支持哪些嵌入Web容器?
前端·spring boot·后端
疯狂成瘾者15 小时前
后端Spring Boot 核心知识点
java·spring boot·后端
IT 行者16 小时前
Spring Boot 4.x 安全监控新篇章:基于 ObservationFilterChainDecorator 的可观测性实践
java·spring boot·后端
小肖爱笑不爱笑16 小时前
JDBC Mybatis
数据库·mybatis
pyniu16 小时前
Spring Boot租房管理系统
java·spring boot·后端
野生技术架构师16 小时前
TokenRetryHelper 详解与 Spring Boot 迁移方案
java·spring boot·后端
IT 行者16 小时前
告别硬编码!Spring Boot 优雅实现 Controller 路径前缀统一管理
数据库·spring boot·python
爱吃山竹的大肚肚16 小时前
Kafka中auto-offset-reset各个选项的作用
java·spring boot·spring·spring cloud
yangminlei16 小时前
Spring Boot+EasyExcel 实战:大数据量 Excel 导出(高效无 OOM)
spring boot·后端·excel