Mybatis-Plus多数据源使用多线程时失效的问题

Posted 虚惊一百场

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Mybatis-Plus多数据源使用多线程时失效的问题相关的知识,希望对你有一定的参考价值。

最近遇到了一个大boss亲自负责的项目,为了快速交付,避免007,所以用到了mybatis-plus多数据源来处理跨库的情况。正当发际线稳步靠近脚后跟的过程中,遇到了一特别不起眼的功能:需要在每个库里都查一点数据,然后在代码里做数据的汇总。

这种比芝麻还小的功能,确实不值得写一篇文章来占用宝贵的互联网资源。但是,在按照我自己的想法实现这个功能时,出问题了。

想法特别简单:当需要查询n个数据库时,我创建n个线程,每个线程去对应的库里拿到数据。

Mybatis-Plus多数据源使用也是极为方便,使用@DS注解即可。但是不管加在类上还是加在实现接口的方法上,均不能正确的找到对应的数据库,所有的线程都抓着主数据库不放。

几经周折,多次试验,最终将多数据源的注解声明在了Callable实现类的call方法上,并且需要用编码的方式,设置当前线程数据源名称,并在当前线程执行结束后,再将其清除掉。

import com.baomidou.dynamic.datasource.annotation.DS;
import com.baomidou.dynamic.datasource.toolkit.DynamicDataSourceContextHolder;

    @Override
    public Future<Map<String, Object>> getTableOverview(CountDownLatch latch) {
        return executor.submit(new Callable<Map<String, Object>>() {
            @DS("slave")
            @Override
            public Map<String, Object> call() throws Exception {
                // 设置当前线程数据源
                DynamicDataSourceContextHolder.push("slave");
                Map<String, Object> result;
                try {
                    // 查询数据库方法
                    result = getTableData();
                } finally {
                    latch.countDown();
                    // 强制清空本地线程,防止内存泄漏,手动调用push可调用此方法确保清除
                    DynamicDataSourceContextHolder.clear();
                }
                return result;
            }
        });
    }

珍爱秀发,远离编码

以上是关于Mybatis-Plus多数据源使用多线程时失效的问题的主要内容,如果未能解决你的问题,请参考以下文章

mybatis-plus自定义多数据源,动态切换数据源事务失效问题

使用线程池时,多线程之间上下文参数传递失效解决办法

使用线程池时,多线程之间上下文参数传递失效解决办法

mybatis-plus多租户的使用

网卡速率变化导致paramiko模块timeout的失效,多线程超时控制解决办法。

springMVCspring控制反转依赖注入MyBatisspringBootspringSecurityJava多线程Redis(缓冲击穿,穿透雪崩热点数据集中失效)