上一篇中讲了mybatis拦截器的实现

这一篇扩展mybatis在拦截器中添加额外参数

在mybatis的mapper.xml文件中,我们可以使用#{}或${}的方式获取到参数,这些参数都需要提前我们在mapper.java接口文件中通过参数的方式传入参数才能取到

为了扩展参数,我们需要了解mybatis是怎么帮我们保管mapper.java中传入的参数的

进入Executor.java接口查看query方法,可以看到第一个参数MappedStatement对象中有一个parameterMap字段,该字段是Map类型保存我们的参数,那我们只需要在拦截器中对MappedStatement对象的parameterMap中put自己想要的参数即可

代码如下


/*** 部门数据拦截器** @author zhangxing* @date 2021/4/12*/
@Intercepts({@Signature(type = Executor.class, method = "query", args = {MappedStatement.class, Object.class, RowBounds.class, ResultHandler.class}),@Signature(type = Executor.class, method = "query", args = {MappedStatement.class, Object.class, RowBounds.class, ResultHandler.class, CacheKey.class, BoundSql.class})
})
public class DeptDataScopeInterceptor implements Interceptor {@Overridepublic Object intercept(Invocation invocation) throws Throwable {Object[] args = invocation.getArgs();if (ArrayUtils.isNotEmpty(args)) {MappedStatement mappedStatement = (MappedStatement) args[0];DataScope dataScope = getDataScope(mappedStatement);StringBuilder sqlString = new StringBuilder();if (dataScope != null) {Long companyOrgId = SecurityUtils.getCompanyOrgId();if (companyOrgId != null) {sqlString.append(StringUtils.format(" {}.{} = {} ", dataScope.orgAlias(), dataScope.orgColumnName(), companyOrgId));} else {sqlString.append(" 1=0 ");}}if (args[1] == null) {args[1] = new MapperMethod.ParamMap<>();}Map map = (Map) args[1];// 此处为重点map.put("dataScope", sqlString.length() > 0 ? " (" + sqlString.toString() + ")" : "");}return invocation.proceed();}private DataScope getDataScope(MappedStatement mappedStatement) {String id = mappedStatement.getId();// 获取 Class MethodString clazzName = id.substring(0, id.lastIndexOf('.'));String mapperMethod = id.substring(id.lastIndexOf('.') + 1);Class<?> clazz;try {clazz = Class.forName(clazzName);} catch (ClassNotFoundException e) {return null;}Method[] methods = clazz.getMethods();DataScope dataScope = null;for (Method method : methods) {if (method.getName().equals(mapperMethod)) {dataScope = method.getAnnotation(DataScope.class);break;}}return dataScope;}@Overridepublic Object plugin(Object target) {return Plugin.wrap(target, this);}@Overridepublic void setProperties(Properties properties) {}}

在map中加入dataScope后,即可在相应的mapper.xml中使用#{dataScope}或${dataScope}或取到该参数

如果项目中使用了pageHelper插件,则启动项目后,执行到对应的mapper查询的时候,如果mapper.xml中使用了上述方式添加的参数,那么项目会报错,因为pageHelper的拦截器会在我们的拦截器之前执行,pageHelper的拦截器中对参数进行了校验,因为自定的拦截器还没有执行,则Map中不会有自定义参数,当pageHelper的拦截器开始校验参数的时候就会报错找不到参数

如何将自定义的拦截器放在PageHelper拦截器前方执行
查阅资料后发现SqlSessionFactory中加入的拦截器,先加入的会后执行,后加入的先执行,那么我们需要让自定义的拦截器在PageHelper后加入,查看PageHelper的自动配置类

pageHelper的拦截器会在Mybatis的自动配置后在做相应配置,那么我们可以写一个配置类,让他在PageHelper的配置类后再执行

代码如下

/*** @author zhangxing* @date 2021/4/11*/
@Configuration
@ConditionalOnBean({SqlSessionFactory.class})
@AutoConfigureAfter(PageHelperAutoConfiguration.class)
public class DeptDataScopeInterceptorConfig {@Autowiredprivate List<SqlSessionFactory> sqlSessionFactoryList;@PostConstructpublic void addPageInterceptor() {DeptDataScopeInterceptor interceptor = new DeptDataScopeInterceptor();for (SqlSessionFactory sqlSessionFactory : sqlSessionFactoryList) {sqlSessionFactory.getConfiguration().addInterceptor(interceptor);}}}

此处需要注意的是,如果DeptDataScopeInterceptorConfig配置类会被SpringBoot项目自动扫描到,尽管配置的顺序是在PageHelper自动配置后再配置,但是被SpringBoot扫描到的配置类会优先加载,所以要防止SpringBoot扫描带该配置,有如下几种方案

  • 如果该配置类已经会被扫描到,则可以使用排出的方式排除掉该类,然后用spring.factories的方式做自动配置
    可以使用@SpringBootApplication(exclude = DeptDataScopeInterceptorConfig.class)
    @ComponentScan(excludeFilters = @ComponentScan.Filter(type = FilterType.ASSIGNABLE_TYPE, value = DeptDataScopeInterceptorConfig.class))
    @EnableAutoConfiguration(exclude = DeptDataScopeInterceptorConfig.class)的方式排出,然后添加到spring.factories中
    文件路径地址resrouces/META-INF/spring.factories
org.springframework.boot.autoconfigure.EnableAutoConfiguration=\top.sclf.common.datascope.config.DeptDataScopeInterceptorConfig

mybatis拦截器添加额外参数相关推荐

  1. mybatis拦截器开发-分表插件

    相关源码已上传至我的github,对应的插件代码在src/main/java/net/dwade/plugins/mybatis目录 https://github.com/huangxfchn/dwa ...

  2. 关于Mybatis拦截器的使用

    关于Mybatis拦截器的使用 1 Mybatis拦截器的使用 1 自定义拦截器 1 Interceptor接口 2 @Intercepts注解 3 @Signature注解 2 注册拦截器 3 拦截 ...

  3. 犯罪心理解读Mybatis拦截器

    原文链接:"犯罪心理"解读Mybatis拦截器 Mybatis拦截器执行过程解析 文章写过之后,我觉得 "Mybatis 拦截器案件"背后一定还隐藏着某种设计动 ...

  4. insert into select 主键自增_springboot2结合mybatis拦截器实现主键自动生成

    点击上方蓝字关注我们 1 01 前言 前阵子和朋友聊天,他说他们项目有个需求,要实现主键自动生成,不想每次新增的时候,都手动设置主键.于是我就问他,那你们数据库表设置主键自动递增不就得了.他的回答是他 ...

  5. by mybatis 自定义order_springboot2结合mybatis拦截器实现主键自动生成

    点击上方蓝字关注我们 1 01 前言 前阵子和朋友聊天,他说他们项目有个需求,要实现主键自动生成,不想每次新增的时候,都手动设置主键.于是我就问他,那你们数据库表设置主键自动递增不就得了.他的回答是他 ...

  6. 真正理解mybatis拦截器以及Interceptor和Plugin作用

    看了很多博客文章和,mybatis 的拦截器概念还是不能很好理解, 可能是因为自己基础不好或者理解方式和他人不同吧,所以决定自己花时间好好捋捋, 然后把理解后的总结记录下来,供他人参考,也许你们的理解 ...

  7. SpringBoot2整合Mybatis拦截器,拦截mapper接口的某个方法

    需求: 在执行某个动态sql时,where 子句,希望通过用户进行自定义查询条件,比如用户可以传入 "id > 100011 and name = '张三'" 的多条件表达式 ...

  8. 定义Mybatis拦截器动态切换postgre数据库schema

    背景 随着业务的发展和合规要求,产品数据库将切换到Postgres.之前不同技术域,不同交付工程的数据分库管理的方式切换到PG数据库后将通过分schema管理. ORM继续使用Mybatis,为使用迁 ...

  9. 拦截器HandlerInterceptor+方法参数解析器HandlerMethodArgumentResolver用于统一获取当前登录用户信息

    文章目录 前言 一.拦截器+方法参数解析器 是什么? 二.具体实现步骤 1.自定义权限拦截器LoginInterceptor拦截所有request请求,并将token解析为currentUser,最终 ...

最新文章

  1. Objective-c 网络编程1 Web请求和响应
  2. 安卓scrollview无法滑动_安卓上线前,小光有话想对你们说
  3. [INS-08109] Unexpected error occurred while validating inputs at state 'getOCMDetails'.
  4. html 跟随鼠标移动线条,canvas跟随鼠标移动的随机线条
  5. LNK2019:无法解析的外部符号
  6. God of War Ascension / 战神4, 再一次迎来新导演!
  7. 详解BSCI实验一、配置EIGRP 验证,汇总
  8. C#实现多人视频聊天
  9. 关于大学生是否沉迷游戏的报告
  10. java mysql sqlhelper_Java访问MySQL数据库的SqlHelper类以及测试程序
  11. VIRTIO-BLK设备SERIAL ID
  12. 计算机应用中双绞线细铜线几根,《计算机应用基础_在线作业_E100.doc
  13. 02 编辑素材和Tilemap
  14. 2018年的总结和2019年的期望
  15. 阿里云和华为云各自的优势
  16. zblog host php,zblog获取当前页面的URL信息
  17. 用c#开发微信 (15) 微活动 1 大转盘
  18. Dijkstra算法和Floyd算法对比分析
  19. OA软件厂商的综合素质到底有多重要?
  20. 不积跬步无以至千里001

热门文章

  1. PLC计数器例子——3个计数器构成的24小时时钟
  2. thinkadmin按配置上传文件至本地,七牛云或阿里oss
  3. Matlab扫雷记录01-matlab中获得向量非零元素个数
  4. 针对Android平台播放器开源库NiceVieoPlayer倍速的开发
  5. BeiJing2006 狼抓兔子
  6. Masonry约束自定义TableViewCell自适应行高的约束冲突的问题
  7. element plus之el-table行融合+列融合+小计行+自定义控件+样式自定义方案
  8. 10万行代码电商项目
  9. 快速查找MySQL数据库中表编码字符集,再修改为指定字符集
  10. python时间函数纳秒_python 时间 纳秒_Pandas时间序列(翻译)