Mybatis 拦截器(Intercept) 修改Sql
-
向mybatis的sql的拦截器列表添加自定义拦截器
import org.apache.ibatis.session.SqlSessionFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Configuration;
import javax.annotation.PostConstruct;
import java.util.List;/*** ** @author CJJ* @version 1.0* @createDate 2021/04/25 13:42* @see com.suncnpap.intelligentqa.common.config.mybatisplus*/@Configuration
public class MybatisConfig {@Autowiredprivate List sqlSessionFactoryList;@PostConstructpublic void addMySqlInterceptor() {SqlInterceptor interceptor = new SqlInterceptor();for (SqlSessionFactory sqlSessionFactory : sqlSessionFactoryList) {sqlSessionFactory.getConfiguration().addInterceptor(interceptor);}}
}
实现Interceptor接口,创建自定义拦截器类
import cn.hutool.core.collection.CollectionUtil;
import com.baomidou.mybatisplus.core.toolkit.PluginUtils;
import lombok.Setter;
import lombok.experimental.Accessors;
import org.apache.ibatis.executor.statement.StatementHandler;
import org.apache.ibatis.mapping.BoundSql;
import org.apache.ibatis.mapping.MappedStatement;
import org.apache.ibatis.plugin.*;
import org.apache.ibatis.reflection.MetaObject;
import org.apache.ibatis.reflection.SystemMetaObject;
import org.apache.ibatis.session.RowBounds;import java.lang.reflect.Field;
import java.sql.Connection;/*** @author Aaron* @desc 分页拦截器* @since 2016-01-23*/
@Setter
@Accessors(chain = true)
@Intercepts({@Signature(type = StatementHandler.class, method = "prepare", args = {Connection.class, Integer.class})})
public class SqlInterceptor implements Interceptor {/*** Physical Page Interceptor for all the queries with parameter {@link RowBounds}*/@SuppressWarnings("unchecked")@Overridepublic Object intercept(Invocation invocation) throws Throwable {StatementHandler statementHandler = PluginUtils.realTarget(invocation.getTarget());MetaObject metaObject = SystemMetaObject.forObject(statementHandler);MappedStatement mappedStatement = (MappedStatement) metaObject.getValue("delegate.mappedStatement");// 全局已删除和未删除数据的修改操作,将deleted条件去掉,保证数据修改成功String id = mappedStatement.getId();if (filterMethodById(id)) {//通过MetaObject优雅访问对象的属性,这里是访问statementHandler的属性;:MetaObject是Mybatis提供的一个用于方便、//优雅访问对象属性的对象,通过它可以简化代码、不需要try/catch各种reflect异常,同时它支持对JavaBean、Collection、Map三种类型对象的操作。//先拦截到RoutingStatementHandler,里面有个StatementHandler类型的delegate变量,其实现类是BaseStatementHandler,然后就到BaseStatementHandler的成员变量mappedStatementString sqlCommandType = mappedStatement.getSqlCommandType().toString();BoundSql boundSql = statementHandler.getBoundSql();//获取到原始sql语句String sql = boundSql.getSql();String mSql = sql.replaceAll("deleted=\\d", " 1=1 ");System.out.println(mSql);//通过反射修改sql语句Field field = boundSql.getClass().getDeclaredField("sql");field.setAccessible(true);field.set(boundSql, mSql);}return invocation.proceed();}@Overridepublic Object plugin(Object target) {if (target instanceof StatementHandler) {return Plugin.wrap(target, this);}return target;}/*** 根据获取到执行 id 找到对应的方法** @param id 根据 MappedStatement 获取到的 id 属性* @return 是否是 searchByQuery 方法*/private boolean filterMethodById(String id) {String[] split = id.split("\\.");return CollectionUtil.contains(CollectionUtil.newArrayList("selectById", "updateById"), split[split.length - 1]);}
}
mybatis的Interceptor的用法,自行百度,使用说明
本文来自互联网用户投稿,文章观点仅代表作者本人,不代表本站立场,不承担相关法律责任。如若转载,请注明出处。 如若内容造成侵权/违法违规/事实不符,请点击【内容举报】进行投诉反馈!
