MybatisPlus
创始人
2024-05-02 22:44:47

1.不用写mapper.xml映射文件,让接口继承自basemapper即可。

数据库中表的字段必须和user类中的字段一摸一样,数据库中的表必须叫user

只能进行简单的crud操作。

package com.atguigu.rj1192.springboot630.mapper;import com.atguigu.rj1192.springboot630.pojo.User;
import com.baomidou.mybatisplus.annotation.TableName;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import org.apache.ibatis.annotations.Mapper;//只需要继承自basemapper接口,就可以实现该方法
//数据库中有一个user表,对应我们的user类
//@Mapper
public interface UserMapper extends BaseMapper {
}

2.当实体类和表名不一致时,可以在实体类指定表名

package com.atguigu.rj1192.springboot630.pojo;import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableName;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import lombok.ToString;@Data
@ToString
@TableName("users")//当实体类和表名不一致的时候,用@tablename来指定表名
public class User {@TableField(exist = false)public String tons;//类中有,但是表中没有的属性public int id;public String username;public String password;
}

2.service层

userservice接口要继承自IService

package com.atguigu.rj1192.springboot630.service.impl;import com.atguigu.rj1192.springboot630.pojo.User;
import com.baomidou.mybatisplus.extension.service.IService;
import org.springframework.stereotype.Service;import java.util.Collection;@Service
public interface UserService extends IService {}

Userserviceimpl实现类要继承自ServiceImpl

第一个参数代表要使用哪个mappper映射文件
第二个参数代表要操作的数据类型

package com.atguigu.rj1192.springboot630.service;import com.atguigu.rj1192.springboot630.mapper.UserMapper;
import com.atguigu.rj1192.springboot630.pojo.User;
import com.atguigu.rj1192.springboot630.service.impl.UserService;
import com.baomidou.mybatisplus.extension.service.IService;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;@Service
//第一个参数代表要使用哪个mappper映射文件
//第二个参数代表要操作的数据类型
public class UserServiceimpl extends ServiceImpl  implements UserService{}

controller层调用的时候 

    @RequestMapping("/")public ModelAndView index() {ModelAndView mav = new ModelAndView();mav.setViewName("index");
//        将要查询出来的user类型的数据,转换成wrapper类型。QueryWrapper wrapper = new QueryWrapper<>();Collection users=userService.list(wrapper);mav.addObject("users", users);return mav;}

3.mybatisplus主键自增

 IdType.INPUT IdType.None 不自增 ,需要用户设置id,一般用input
 IdType.ASSIGN_UUID varchar类型     IdType.ASSIGN_ID bigint类型 雪花算法生成随机id

插入新数据时不用管id,会自增的。

其他的主键自增方法还有:

1》mysql自增,缺点是如果做了分库分表,需要查询最大的id后,+1才能插入新数据,比较耗时间

2》uuid 缺点是无法排序,每次都生成唯一且随机的

3》redis集群 原子操作

@Data
public class User {
//    IdType.INPUT IdType.None 不自增 ,需要用户设置id,一般用input
//    IdType.ASSIGN_UUID varchar类型     IdType.ASSIGN_ID bigint类型 雪花算法生成随机id@TableId(type = IdType.ASSIGN_ID)private Long id;private String name;private Integer age;private String email;@TableField(fill = FieldFill.INSERT)private Date createTime;//    添加和修改时都有值@TableField(fill = FieldFill.INSERT_UPDATE)private Date updateTime;
}

4.mybatisplus修改时间和添加时间自动填充

(1)数据库表中添加自动填充字段

在User表中添加datetime类型的新的字段 create_time、update_time

(2)实体上添加注解 

FieldFill.INSERT  在插入新数据时执行对应的方法(第三步定义)

FieldFill.INSERT_UPDATE 在插入和更新数据时执行对应的方法(第三步定义)

@Data
public class User {
//    IdType.INPUT IdType.None 不自增 ,需要用户设置id,一般用input
//    IdType.ASSIGN_UUID varchar类型     IdType.ASSIGN_ID bigint类型 雪花算法生成随机id@TableId(type = IdType.ASSIGN_ID)private Long id;private String name;private Integer age;private String email;@TableField(fill = FieldFill.INSERT)private Date createTime;//    添加和修改时都有值@TableField(fill = FieldFill.INSERT_UPDATE)private Date updateTime;
}

(3)编写实际的填充类和填充方法


@Component
public class MyMetaObjectHandler implements MetaObjectHandler {private static final Logger LOGGER = LoggerFactory.getLogger(MyMetaObjectHandler.class);//使用mp执行添加操作,会执行@Overridepublic void insertFill(MetaObject metaObject) {//MetaObject 原数据对象  数据库名 表名等信息LOGGER.info("开始添加填充 ....");this.setFieldValByName("createTime", new Date(), metaObject);this.setFieldValByName("updateTime", new Date(), metaObject);}//    使用mp执行更新操作,会执行@Overridepublic void updateFill(MetaObject metaObject) {LOGGER.info("开始更新填充 ....");this.setFieldValByName("updateTime", new Date(), metaObject);}}

(4)在修改和插入时就会自动填充修改时间和插入时间。

    @Testvoid updateuser() {User user = new User();
//        不需要去设置id值,mp会帮我们自动生成id值user.setAge(555);user.setId(102l);//        返回结果是影响的行数System.out.println("修改影响的行数:" + userMapper.updateById(user));}

5.mybatisplus设置乐观锁

 mike工资是五千 管理员a 要将工资修改为8000       管理员b要将工资减少两千

a和b同时修改,同时拿到修改前的5000

a修改工资为8000,提交事务。

a提交事务后,b修改工资5000-2000=3000,b将工资修改为3000

mike的工资变成了3000,而不是6000,就造成了丢失更新问题

乐观锁和悲观锁可以解决丢失更新问题

乐观锁:设置一个版本号,管理员在修改数据前,需要先获得版本号

               管理员a和b同时获得1版本,a修改完了提交,数据变成2版本,b修改完了提交,发现数据已经变成2版本了,则b管理员提交失败。

悲观锁:不允许两个管理员同时修改一条数据,必须等一个修改完一个才能修改

1》数据库中添加version字段 bigint类型

2》实体类中添加version字段,并添加@Version注解

并通过@TableField(fill = FieldFill.INSERT)设置添加新记录时给verison默认值1


@Data
public class User {//    IdType.INPUT IdType.None 不自增 ,需要用户设置id,一般用input
//    IdType.ASSIGN_UUID varchar类型     IdType.ASSIGN_ID bigint类型 雪花算法生成随机id@TableId(type = IdType.ASSIGN_ID)private Long id;private String name;private Integer age;private String email;@Version@TableField(fill = FieldFill.INSERT)private Integer version;@TableField(fill = FieldFill.INSERT)private Date createTime;//    添加和修改时都有值@TableField(fill = FieldFill.INSERT_UPDATE)private Date updateTime;
}

设置添加新记录时给verison默认值1

this.setFieldValByName("version", 1, metaObject);

(上面添加新纪录时间自动填充的步骤一样)

@Component
public class MyMetaObjectHandler implements MetaObjectHandler {private static final Logger LOGGER = LoggerFactory.getLogger(MyMetaObjectHandler.class);//使用mp执行添加操作,会执行@Overridepublic void insertFill(MetaObject metaObject) {//MetaObject 原数据对象  数据库名 表名等信息LOGGER.info("开始添加填充 ....");this.setFieldValByName("createTime", new Date(), metaObject);this.setFieldValByName("updateTime", new Date(), metaObject);this.setFieldValByName("version", 1, metaObject);}//    使用mp执行更新操作,会执行@Overridepublic void updateFill(MetaObject metaObject) {LOGGER.info("开始更新填充 ....");this.setFieldValByName("updateTime", new Date(), metaObject);}

3》配置乐观锁插件

在mybatisplus设置类中 设置乐观锁插件

(在这个类中配置@mapperscan注解,这个注解尽量不写在启动类上,而是写在mp配置类中。)

@MapperScan("com.example.mp1229.mapper")
@Configuration
public class MPconfig {
//    乐观锁插件@Beanpublic MybatisPlusInterceptor mybatisPlusInterceptor() {MybatisPlusInterceptor interceptor = new MybatisPlusInterceptor();interceptor.addInnerInterceptor(new OptimisticLockerInnerInterceptor());return interceptor;}
}

4》需要先查询出来,再修改    在修改之后,会发现该数据的verision增加了1

    //测试乐观锁@Testvoid testOptimisticLocker() {User user = userMapper.selectById(102l);
//        不需要去设置id值,mp会帮我们自动生成id值user.setAge(10);//        返回结果是影响的行数System.out.println("修改影响的行数:" + userMapper.updateById(user));}

 模拟取出数据后,数据库中version实际数据比取出的值大,即已被其它线程修改并更新了version

    //测试乐观锁@Testvoid testOptimisticLocker() {User user = userMapper.selectById(102l);
//        不需要去设置id值,mp会帮我们自动生成id值user.setAge(10);
//       模拟取出数据后,数据库中version实际数据比取出的值大,即已被其它线程修改并更新了versionuser.setVersion(user.getVersion()-1);//        返回结果是影响的行数System.out.println("修改影响的行数:" + userMapper.updateById(user));}

6.逻辑删除

逻辑删除:假删除,将对应数据中代表是否被删除字段状态修改为“被删除状态”,之后在数据库中仍旧能看到此条数据记录

1)数据库中添加 deleted字段

2)mybatisplus实体类中添加deleted字段,并设置默认值 0 (未删除)   和上面一样。

user类

    @TableField(fill = FieldFill.INSERT)private Integer deleted;
MyMetaObjectHandler类
  //使用mp执行添加操作,会执行@Overridepublic void insertFill(MetaObject metaObject) {//MetaObject 原数据对象  数据库名 表名等信息LOGGER.info("开始添加填充 ....");this.setFieldValByName("createTime", new Date(), metaObject);this.setFieldValByName("updateTime", new Date(), metaObject);this.setFieldValByName("version", 1, metaObject);
//        添加新数据时,逻辑已删除值设置为0,未删除this.setFieldValByName("deleted",0,metaObject);}

3)application.yaml配置逻辑删除字段,删除和未删除对应的 逻辑值

mybatis-plus:global-config:db-config:logic-delete-field: deleted # 全局逻辑删除的实体字段名( 3.3.0 版本后,配置后可以忽略不配置步骤2)logic-delete-value: 1 # 逻辑已删除值(默认为 1)logic-not-delete-value: 0 # 逻辑未删除值(默认为 0)

4)使用deletebyid 删除即可

@Testvoid logcaldel(){int result=userMapper.deleteById(1608419885151080450l);System.out.println("逻辑删除结果"+result);}
5)查询所有 会自动携带查询deleted为0的数据
@Test
void findall() {System.out.println(userMapper.selectList(null));
}

 

相关内容

热门资讯

北京的名胜古迹 北京最著名的景... 北京从元代开始,逐渐走上帝国首都的道路,先是成为大辽朝五大首都之一的南京城,随着金灭辽,金代从海陵王...
苗族的传统节日 贵州苗族节日有... 【岜沙苗族芦笙节】岜沙,苗语叫“分送”,距从江县城7.5公里,是世界上最崇拜树木并以树为神的枪手部落...
世界上最漂亮的人 世界上最漂亮... 此前在某网上,选出了全球265万颜值姣好的女性。从这些数量庞大的女性群体中,人们投票选出了心目中最美...
长白山自助游攻略 吉林长白山游... 昨天介绍了西坡的景点详细请看链接:一个人的旅行,据说能看到长白山天池全凭运气,您的运气如何?今日介绍...