项目文件总览
Dao层中
domain层中
测试类中含有三个测试方法,分别对应,插入删除和修改
id生成策略
针对不同的场景使用不同的id,用到提供的一个注解@TableId
在实体类中使用@Tablefiled注解时可以看见有如下的多种策略
使用第一个AUTO策略
运行插入方法得到
在数据库表格中成功实现递增
在@TableId注解中还有多种策略
NONE是没有策略,input是用户输入
下面三个带注解的是过时的,UUID由上面的ASSIGN_UUID替代
三个key值为3的涉及到雪花算法生成ID,ID_WORKER生成整数,ID_WORKER_STR生成字符串
合并为了ASSIGN_ID
使用INPUT策略
要先把数据库表格上的自增关闭
先后修改实体类属性Id上策略
然后如果使用上面的方法,不指定ID直接insert的话就会报错
提示id不能为空
@Test
void testSave() {
mpdb mpdb=new mpdb();
mpdb.setName("鼠鼠一号");
mpdb.setAge(22);
mpdb.setTel("123456");
mpdb.setPassword("pw1");
mpdb.setId(666L);
userDao.insert(mpdb);
}
使用上面的设置ID的测试方法后就又可以了
使用雪花算法策略
修改策略
@TableId(type = IdType.ASSIGN_ID)
private Long id;
然后还是上面的代码setID(666L)注释掉
@Test
void testSave() {
mpdb mpdb=new mpdb();
mpdb.setName("鼠鼠一号");
mpdb.setAge(22);
mpdb.setTel("123456");
mpdb.setPassword("pw1");
//mpdb.setId(666L);
userDao.insert(mpdb);
}
运行得
可以看见ID为一长串的数字
雪花算法生成的是一个64位的数字串,所以使用L来存,64位分为如下
ID生成策略扩展(全局设置):
对应实体类上的id也可以不用加上那个@TableId注解
在配置文件的mybatis-plus配置项中如下
然后就可以删除实体类上的@TableFiled注解了
全局配置还可以配置表名映射等。
多数据操作(删除与查询)
使用deleteBAtchIds()方法,传进去一个集合参数,装了要删除的id
@Test
void testDelete() {
List<Long> list=new ArrayList<Long>();
list.add(4L);
list.add(5L);
list.add(666L);
userDao.deleteBatchIds(list);
}
运行后可以看见相应数据已经没了
这里也可按照多个ID进行查询,使用的方法是selectBatchIds(),效果一样
逻辑删除
应用场景如下,一个员工表和一个业绩表,当删除一个员工时会连带业绩一起删除
当统计数据时会出现脏数据,因此在表后增加一个删除字段用于逻辑删除。
首先修改数据库增加一个deleted字段并设置默认值0
在实体类中增加逻辑删除字段,并增加一个@TableLogic注解表明是一个逻辑删除字段
并为注解设置两个参数,vlaue是没有删除,delval是删除了,要和数据库对应
@TableLogic(value="0",delval = "1")
使用如下的语句进行删除操作
userDao.deleteById(1L);
查看数据库可以看见数据没有删除,而是改了deleted为1
这里的注解内部应该就是一个update语句了
控制台日志也可以看见就是一个update操作
然后经过逻辑删除后,再次查询全集时就看不见id为1的数据了,会自动跳过
如果想要看见全部数据就要在DAO层自己写SQL语句。
逻辑删除的注解也可以在配置文件里面进行定义
在配置文件定义之后,就不需要在实体类上加注解了,只要提供相应字段即可
乐观锁(应对并发)
锁用于解决并发引起的问题
场景有:
由于业务是并发的,不加锁的话可能会出现-1,-2
这个方案可以解决一些请求量较小的场景,比如2000个请求以下
第一步
在数据库表结构加上一个version字段表明当前谁在操作该数据,int类型
并在实体类也加上一个Integer类型数据并加上一个@Version注解
使用update set abc=1,version=version+1 where version=? 这个格式保证每个人拿到的version都是不同的.
这里要像执行分页查询时一样,开启一个拦截器实现在update语句后面加默认语句
@Test
void testUpdate(){
mpdb mpdb=new mpdb();
mpdb.setId(1L);
mpdb.setName("鼠鼠2号");
mpdb.setVersion(1);
userDao.updateById(mpdb);
}
运行得sql语句里面有了两个version
因此可以发现,要修改之前要先获取即可修改的数据的version
//1.先通过id将数据查询出来
mpdb mpdb=userDao.selectById(3L);
//2.将要修改的属性逐一设置进去
mpdb.setName("北岭");
userDao.updateById(mpdb);
这里加锁的实现方法就是两个用户拿到了同一个version,但是其中一个执行完后修改了version版本导致另一个人的update失效了