目录
乐观锁和悲观锁
测试乐观锁单线程成功的例子
乐观锁多线程失败案例
查询操作
分页查询
删除操作
删除单个
删除多个
按map删除
逻辑删除
乐观锁:顾名思义十分乐观,他总是认为不会出现问题,无论干什么都不去上锁,如果出现了问题,在次更新值测试
在数据库中新增字段version,在实体类中也要增加对应的,使用@Version表示他是一个乐观锁
乐观锁:先查询,获取它的版本号,然后在一系列的操作后,让他的版本号+1,前提是这个版本号还是之前查出来的那个版本号。
@Version//乐观锁
private Integer version;
写一个配置类
@Configuration
@MapperScan("com.mapper")
public class MyBatisPlusConfig {@Beanpublic MybatisPlusInterceptor mybatisPlusInterceptor() {MybatisPlusInterceptor interceptor = new MybatisPlusInterceptor();interceptor.addInnerInterceptor(new OptimisticLockerInnerInterceptor());return interceptor;}}
更新下
@Testvoid update() {User user = userMapper.selectById(5L);user.setName("kongchaoAfter");user.setAge(21);user.setEmail("kc@qq.com");userMapper.updateById(user);}
说明:
newVersion = oldVersion + 1
newVersion
会回写到 entity
中updateById(id)
与 update(entity, wrapper)
方法update(entity, wrapper)
方法下, wrapper
不能复用!!!
@Testvoid update2() {//线程1User user = userMapper.selectById(5L);user.setName("kongchao1");user.setAge(11);user.setEmail("kc1@qq.com");//模拟另一个线程插队User user2 = userMapper.selectById(5L);user2.setName("kongchao2");user2.setAge(22);user2.setEmail("kc2@qq.com");userMapper.updateById(user2);//若没有乐观锁,则会覆盖user2的操作userMapper.updateById(user);}
数据库
运行结果
// 测试查询@Testpublic void testSelectById(){User user = userMapper.selectById(1L);System.out.println(user);
}
// 测试批量查询!@Testpublic void testSelectByBatchId(){List users = userMapper.selectBatchIds(Arrays.asList(1, 2, 3));users.forEach(System.out::println);}
@SpringBootTest
@MapperScan("com.mapper")//扫描mapper,自动创建实现类
class MybatisPlusQuickApplicationTests {@Autowiredprivate UserMapper userMapper;
//按条件查询之一使用map操作@Testpublic void testSelectByBatchIds(){HashMap map = new HashMap<>();// 自定义要查询map.put("name","kc");map.put("age",18);List users = userMapper.selectByMap(map);users.forEach(System.out::println);}
}
在配置类中加入分页插件
@Configuration
@MapperScan("com.mapper")
public class MyBatisPlusConfig {// 分页插件@Beanpublic PaginationInterceptor paginationInterceptor(){return new PaginationInterceptor();}}
在测试类中测试
//测试分页查询@Testpublic void pageTest(){//第一页,每页三个数据Page page=new Page<>(1, 3);userMapper.selectPage(page, null);page.getRecords().forEach(System.out::print);}
可以获取各种参数
运行结果
@Testpublic void deleteById(){userMapper.deleteById(1583366844257988614L);}
//删除多个@Testpublic void deleteByIds(){userMapper.deleteBatchIds(Arrays.asList(1583366844257988612L,1583366844257988613L));}
//通过map删除
@Testpublic void deleteMap(){HashMap hashMap=new HashMap<>();hashMap.put("name", "kc");userMapper.deleteByMap(hashMap);
}
物理删除:从数据库中移除
逻辑删除:数据还存在数据库中,是增加了一个deleted字段,以这个字段作为条件,当字段=1时不显示这条数据
这个功能类似于回收站。并没有真正删除。
在数据库中添加字段deleted然后在实体类中也加入,并带上注解
@TableLogic//逻辑删除private Integer deleted;
在application.yaml配置文件中配置
mybatis-plus:global-config:db-config:
# 没有逻辑删除的显示为0,否则显示1logic-delete-value: 1logic-not-delete-value: 0
测试之前的删除
//逻辑删除单个@Testpublic void deleteById(){userMapper.deleteById(6L);}
运行结果,删除只是将deleted字段变为1
测试查询
// 测试查询@Testpublic void testSelectById(){User user = userMapper.selectById(6L);}
运行结果,发现也会加上deleted=0的条件