如果对 MyBatis-Plus 不了解,请先看 SpringBoot 整合 MyBatis-Plus

一、拦截器

  MyBatis 允许你在已映射语句执行过程中的某一点进行拦截调用。默认情况下,MyBatis 允许使用插件来拦截方法的调用,分别为:Executor(执行器的方法)、ParameterHandler(参数的处理)、ResultSetHandler(结果集的处理)、StatementHandler(SQL 语法构建的处理)。

1、定义自定义拦截器

import org.apache.ibatis.executor.Executor;  
import org.apache.ibatis.mapping.MappedStatement;  
import org.apache.ibatis.plugin.*;  
import java.util.Properties;  
  
@Intercepts({@Signature(  
 type = Executor.class,  
 // 设置指定类型的SQL  
 method = "update",  
 args = {MappedStatement.class,Object.class})})  
public class MyInterceptor implements Interceptor {  
 @Override  
 public Object intercept(Invocation invocation) throws Throwable {  
 // 拦截方法,具体业务逻辑编写的位置  
 return invocation.proceed();  
 }  
  
 @Override  
 public Object plugin(Object target) {  
 // 创建target对象的代理对象,目的是将当前拦截器加入到该对象中  
 return Plugin.wrap(target,this);  
 }  
  
 @Override  
 public void setProperties(Properties properties) {  
 // 属性设置  
 }  
}  

2、注入自定义的拦截器

 @Bean  
 public MyInterceptor myInterceptor(){  
 return new MyInterceptor();  
 }  

二、性能分析插件

  性能分析拦截器,用于输出每条 SQL 语句及其执行时间。该插件 3.2.0 以上版本移除推荐使用第三方扩展 执行 SQL 分析打印 功能。

三、乐观锁插件

  使用场景:当要更新一条记录的时候,希望这条记录没有被别人更新。乐观锁的实现方法:取出记录时,获取当前 version,更新时带上 version,如果 version 不对,则更新失败。

  配置文件

 @Bean  
 public OptimisticLockerInterceptor optimisticLockerInterceptor(){  
	return new OptimisticLockerInterceptor();  
 }  

  为表添加 version 字段并设置初始值为 1,并为实体类添加 version 字段,并且添加@Version 注解。仅支持 updateById(id)和 update(entity,wrapper)方法。
  例子:

 User user = new User();  
 user.setId(2);  
 user.setPassword("101010101");  
 // 当version的值和数据库的version的值相同时才执行  
 user.setVersion(1);  
 // UPDATE tb_user SET user_password=?, user_grade=?, user_version=? WHERE user_id=? AND user_version=?   
 System.out.println(user.updateById());  

四、SQL 注入器

  在 MP 中如果 BaseMapper 中的方法不够用户,该如何添加呢?

1、编写 MyBaseMapper,定义自定义方法。

public interface MyBaseMapper<T> extends BaseMapper<T> {  

	List<T> findAll();  
}  

2、将 Mapper 继承自己编写 MyBaseMapper

public interface UserMapper extends MyBaseMapper<User> {  
}  

3、为自己定义的方法创建类继承 AbstractMethod 。

public class FindAll extends AbstractMethod {  
 	@Override  
 	public MappedStatement injectMappedStatement(Class<?> mapperClass, Class<?> modelClass, TableInfo tableInfo) {  
 		String sqlMethod="findAll";  
 		String sql="select * from "+tableInfo.getTableName();  
 		SqlSource sqlSource=languageDriver.createSqlSource(configuration,sql,modelClass);  
 		// 根据SQL语句的类型调用不同的方法。  
 		return this.addSelectMappedStatementForTable(mapperClass,sqlMethod,sqlSource,tableInfo);  
	}  
}  

4、创建自己的 MySqlInjector,将原来的方法和自定义的方法注入进去。

public class MySqlInjector extends DefaultSqlInjector {  
  
 	@Override  
	public List<AbstractMethod> getMethodList(Class<?> mapperClass) {  
 		List<AbstractMethod> list = new ArrayList<>();  
 		// 获取父类中的集合  
		list.addAll(super.getMethodList(mapperClass));  
		// 扩充自定义的方法  
 		list.add(new FindAll());  
 		return list;  
	}  
}  

5、将自己创建的 MySqlInjector 交给 Spring 管理

 @Bean  
 public MySqlInjector mySqlInjector(){  
	return new MySqlInjector();  
 }  

6、测试

userMapper.findAll()  

五、自动填充功能

  在插入或者更新数据时,我们希望有些字段可以自动填充数据。在 MP 中提供了这样的功能,可以实现自动填充。
  在字段上添加@TableField 注解,例如:

1、修改实体类

@TableField(value = "user_grade",fill = FieldFill.INSERT)  
private int grade;  

2、填充的类型:

作用
DEFAULT默认不处理
INSERT插入时填充字段
UPDATE更新时填充字段
INSERT_UPDATE插入和更新时填充字段

3、配置填充规则:

@Component  
public class MyMetaObjectHandler implements MetaObjectHandler {  
 @Override  
 public void insertFill(MetaObject metaObject) {  
 // 先获取 grade 的值,再进行判断,如果为空,就进行填充。  
 Object grade=getFieldValByName("grade",metaObject);  
 if(((Integer)grade) ==0){  
 setFieldValByName("grade",999,metaObject);  
 }  
 }  
  
 @Override  
 public void updateFill(MetaObject metaObject) {  
  
 }  
}  

4、测试:

User user=new User();  
user.setName("Yi-Xing");  
userMapper.insert(user);  

六、逻辑删除

  所谓逻辑删除就是将数据标记为删除,而并非真正的物理删除(非 DELETE 操作),查询时需要携带状态条件,确保被标记的数据不被查询到。这样做的目的就是避免数据被真正的删除。

1、修改表和实体类

  修改表结构,添加 deleted 字段,用于表示数据是否被删除,1 代表删除,0 代表未删除。同时也修改实体类,添加 deleted 属性并添加@TableLogic 注解

@TableLogic  
@TableField("user_deleted")  
private int deleted;  

2、配置

mybatis-plus:  
 db-config:  
 # 删除状态为1  
 logic-delete-value: 1  
 # 未删除状态为0  
 logic-not-delete-value: 0  

3、测试

userMapper.deleteById(2)  

标题:MyBatis-Plus 的更多功能
作者:Yi-Xing
地址:http://47.94.239.232/articles/2020/01/14/1578992228126.html
博客中若有不恰当的地方,请您一定要告诉我。前路崎岖,望我们可以互相帮助,并肩前行!